Evaluation des arguments multiples et des blocs avec l'héritage en Ruby
Par lucas, dimanche 18 mai 2008 à 22:39 :: General :: #35 :: rss
Ça me servira à la fois de piqûre de rappel quand j'en aurais besoin, et ça peut aider à éclaircir les idées. On oubliera pas de ne pas oublier (oui oui, tout ça, j'insiste) que l'appel à super récupère lui-même le bloc. Ce peut être gênant si on a besoin de faire un yield dans la classe fille en même temps qu'on a besoin d'appeler super. Ceci rend plus difficile le changement de comportement d'une méthode qui detruit des informations quand on lui passe un bloc (par exemple l'ouverture/fermeture automatique des fichiers) : il faut faire son yield à l'intérieur d'un nouveau bloc, selon ce qui passe dans les paramètres du bloc ça peut être plus ou moins facile.
Au niveau des arguments multiples, on oubliera pas de ne pas oublier la différence entre *args et args. Il faut voir ça comme un pointeur sur un objet Array. Également, la classe d'un objet, même quand dans la méthode parente est celle de l'objet hérité, ça pourrait jouer des tours si on fait des tests avec == au lieu de is_a? (je n'ai pas mis dans le test, mais is_a? teste l'appartenance d'un objet à une classe et toutes les classes parentes.
Voici le code qui m'a servit pour tout mettre au clair :
def initialize(*args,&block)
puts args.size
puts self.class
yield self if block_given?
end
end
class SubTest < Test
def initialize(*args)
super(*args)
yield self if block_given?
end
end
class SubSubTest < SubTest
def initialize
super(:un,:dos,:tres) {|l| puts "truc"}
yield self if block_given?
end
end
class SubSubSubTest < SubSubTest
def initialize
super() do |l|
puts "sub-truc"
yield self
end
end
end
Test.new(1,2) {|l| puts l.class}
SubTest.new {|l| puts l.class}
SubSubTest.new {|l| puts l.class}
SubSubSubTest.new {|l| puts l.class}
Et voici le résultat brut de décoffrage :
2 Test Test 0 SubTest SubTest SubTest 3 SubSubTest truc truc SubSubTest 3 SubSubSubTest truc truc sub-truc SubSubSubTest
On notera que le "puts self.class" dans la classe principale rajoute une occurence du texte, j'aurais pû mettre ici (ou équivalent plus bas dans la hierarchie) un "if self.class == Test" ou un "if self.is_a? Test" pour montrer la différence entre les deux.
Si vous avez des questions, questionnez, mais je ne promets rien pour les réponses.
Commentaires
Aucun commentaire pour le moment.
Ajouter un commentaire