Ruby – a fantastic language you don’t know (yet)
Ruby is a dynamic language, and by that I mean that it can add features to itself, it can write self-modifying code, and it can be extended further than you would think was possible.
Say for example that you wanted to define several additional methods for
class Array, you’d write
class Array def max_index_or_minus_1 return length-1 end end
…and all instances of Array can now use method “max_index_or_minus_1”
a = [] ix = a.max_index_or_minus_1
similarly, if you want to define several methods for an object’s singleton class, you write
class << Object define whatnow puts "What? Now?" end end
and all instances of object’s singleton class (i.e., just object) can now access the methods.
Array.whatnow
As for class methods – well, a class is just an instance of class Class. Therefore, it has methods which are instance methods of Class. You can add in methods by saying
class Class def classmethod puts "class method (end of imagination sorry)" end end
and all classes will now have the new class methods.
Array.classmethod
If you want class methods for a single class, you are actually tacking on methods to an object, in much the same way as “def a.newmethod” would. So you can use that syntax:
def Array.newmethod1
#[define]
end
#or you can say
class << Array
#[define]
end
or, if you are already *in* class Array and defining instance methods, you can highlight the fact that you’re working in the same conceptual space by taking advantage of Ruby’s setting ‘self’ to ‘Array’ when you say ‘class Array’, and writing
class Array
def instancemethod
#[define]
end
class << self
def classmethod
#[define]
end
end
end
There’s no arcane magic going on here – self is an object of class Class, and in this case it has the value Array.
Try the following in irb:
class Array
p self
p self.class
end
class << Array
p self
p self.class
end
class Array
class << self
p self
p self.class
end
end
a = Array.new
class << a
p self
p self.class
end
and, to prove that singleton classes are being created, even though they all say Array,
b = Array.new
class << b
p self
end