I’ve been playing with Ruby a little and there’s one feature in Ruby that I particularly like: the ability to extend existing classes. For example, for as long as I’ve been programming using objects I wanted to add a method to integers called “timesSayZef”. So you could do this:
100.timesSayZef()
And it would print “Zef” a hundred times. However, Java doesn’t allow you to do this, C# doesn’t allow you to do this, even Python doesn’t allow you to do this (at least I couldn’t get it to do it). However, Ruby does with this code:
class Fixnum
def timesSayZef
times { puts "Zef" }
end
end
In Ruby when you define a class that already exists (such as Fixnum, which represents a number, such as 100), it will merge the two definitions. So in this case I would add a timesSayZef method to the Fixnum class. When I now do this:
10.timesSayZefit will print:
Zef Zef Zef Zef Zef Zef Zef Zef Zef Zef
Cool huh?
Ruby also allows you to extend existing objects with additional methods. For example:
class BoringClass
def saySomething
puts 'Something'
end
end
module ZefStuff
def sayZefIsCool
puts 'Zef is cool!'
end
end
bc = BoringClass.new
bc.saySomething
bc.extend(ZefStuff)
bc.sayZefIsCool
What I do here is first define a class. Then define a module. Create an instance of the class and then extend that instance with all the methods in the module. This example will print:
Something Zef is cool!
Well.. I guess it would get pretty tricky surrounding performance and conformance.. also it would get tricky getting the type defenitions in some cases synchronised.
I’d rather see ‘wrapper’ like abilities…
So you’d define a class which ‘wraps’ another class and then you’ll be able to cast that existing class to that new wrapping class.
Then you’d use something like:
((IZefTimeSayZefable)(100)).zefSayZef()
Although dynamic languages could see that cast automaticly..
although this makes me wonder whether ruby uses this kind of a wrapping already… :p
Numbers are the only things in Python that are not objects (and the ruby people are quick to point that out).
But you could do this: “Zef”*10 and I don’t know ruby well enough to copy the second code snippet but I’m sure it’s easy with decorators or metaclasses or something.
It couldn’t totaly be I realised…
10 PRINT “Zef” 20 GOTO 10 RUN
I agree with Zef. The ability to dynamically extend classes and objects is indeed one of the most admirable qualities of Ruby. If I’m not mistaken, Ruby on Rails utilizes this capability to a large degree.
“But you could do this: Zef*10″
There are of course other ways of printing Zef ten times, but that’s completely beside the point.
yeah I know, but I had to point it out :P
Dagur, numbers are objects in Python and have been for a long time (perhaps even from the very beginning). They’re just immutable so one can’t modify the number objects nor the number class. But custom objects could be made immutable as well and they wouldn’t be any less “objects”.