165 votes

Comment vous passer des arguments à define_method ?

Je voudrais passer un argument à une méthode définie à l’aide de define_method, comment pourrais-je faire ?

213voto

Kevin Conner Points 5832

Le bloc que vous passez à define_method peut inclure des paramètres. Voilà comment votre méthode définie accepte des arguments. Lorsque vous définissez une méthode que vous êtes vraiment juste surnommant le bloc et conserver une référence à celle-ci dans la classe. Les paramètres sont équipées du bloc. Donc :

104voto

equivalent8 Points 2009

... et si vous voulez des paramètres optionnels

  class Bar
   define_method(:foo) do |arg=nil|                  
     arg                                                                                          
   end   
 end

 a = Bar.new
 a.foo
 #=> nil
 a.foo 1
 # => 1
 

... autant d'arguments que vous voulez

  class Bar
   define_method(:foo) do |*arg|                  
     arg                                                                                          
   end   
 end

 a = Bar.new
 a.foo
 #=> []
 a.foo 1
 # => [1]
 a.foo 1, 2 , 'AAA'
 # => [1, 2, 'AAA']
 

...combinaison de

  class Bar
   define_method(:foo) do |bubla,*arg|
     p bubla                  
     p arg                                                                                          
   end   
 end

 a = Bar.new
 a.foo
 #=> wrong number of arguments (0 for 1)
 a.foo 1
 # 1
 # []

 a.foo 1, 2 ,3 ,4
 # 1
 # [2,3,4]
 

... tous

  class Bar
   define_method(:foo) do |variable1, variable2,*arg, &block|  
     p  variable1     
     p  variable2
     p  arg
     p  block.inspect                                                                              
   end   
 end
 a = Bar.new      
 a.foo :one, 'two', :three, 4, 5 do
   'six'
 end
 

60voto

Jörg W Mittag Points 153275

En plus de la réponse de Kevin Conner: les arguments de bloc ne prennent pas en charge la même sémantique que les arguments de méthode. Vous ne pouvez pas définir d'arguments par défaut ou de bloc.

Ceci n'est corrigé que dans Ruby 1.9 avec la nouvelle syntaxe alternative "stabby lambda" qui prend en charge la sémantique complète des arguments de méthode.

Exemple:

 # Works
def meth(default = :foo, *splat, &block) puts 'Bar'; end

# Doesn't work
define_method :meth { |default = :foo, *splat, &block| puts 'Bar' }

# This works in Ruby 1.9 (modulo typos, I don't actually have it installed)
define_method :meth, ->(default = :foo, *splat, &block) { puts 'Bar' }
 

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X