代码之家  ›  专栏  ›  技术社区  ›  Sixty4Bit

如何传递参数来定义方法?

  •  144
  • Sixty4Bit  · 技术社区  · 18 年前

    我想将参数传递给使用define_方法定义的方法,我该如何做?

    4 回复  |  直到 17 年前
        1
  •  207
  •   easeout    18 年前

    传递给定义_方法的块可以包括一些参数。这就是您定义的方法接受参数的方式。当你定义一个方法的时候,你实际上只是在给这个块做小标记,并在类中保留对它的引用。参数随块一起提供。因此:

    define_method(:say_hi) { |other| puts "Hi, " + other }
    
        2
  •  99
  •   equivalent8    8 年前

    ... 如果你想要可选的参数

     class Bar
       define_method(:foo) do |arg=nil|                  
         arg                                                                                          
       end   
     end
    
     a = Bar.new
     a.foo
     #=> nil
     a.foo 1
     # => 1
    

    ... 尽可能多的争论

     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']
    

    …组合

     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]
    

     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
    

    使现代化

    ** I quote )是否:

    …当然,您也可以在define方法中使用它:)

     class Bar 
       define_method(:foo) do |variable1, variable2,*arg,**options, &block|
         p  variable1
         p  variable2
         p  arg
         p  options
         p  block.inspect
       end 
     end 
     a = Bar.new
     a.foo :one, 'two', :three, 4, 5, ruby: 'is awesome', foo: :bar do
       'six'
     end
    # :one
    # "two"
    # [:three, 4, 5]
    # {:ruby=>"is awesome", :foo=>:bar}
    

     class Bar
       define_method(:foo) do |variable1, color: 'blue', **other_options, &block|
         p  variable1
         p  color
         p  other_options
         p  block.inspect
       end
     end
     a = Bar.new
     a.foo :one, color: 'red', ruby: 'is awesome', foo: :bar do
       'six'
     end
    # :one
    # "red"
    # {:ruby=>"is awesome", :foo=>:bar}
    

    我试图创建一个包含关键字argument、splat和double splat的示例:

     define_method(:foo) do |variable1, variable2,*arg, i_will_not: 'work', **options, &block|
        # ...
    

    或

     define_method(:foo) do |variable1, variable2, i_will_not: 'work', *arg, **options, &block|
        # ...
    

    摘要文章: https://blog.eq8.eu/til/metaprogramming-ruby-examples.html

        3
  •  60
  •   Jörg W Mittag    17 年前

    除了Kevin Conner的回答之外:块参数不支持与方法参数相同的语义。不能定义默认参数或块参数。

    这仅在Ruby1.9中通过支持完整方法参数语义的新的替代“ThankyLambda”语法修复。

    例子:

    # 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' }
    
        4
  •  8
  •   Andy Ali    10 年前

    https://robots.thoughtbot.com/ruby-2-keyword-arguments

    define_method(:method) do |refresh: false|
      ..........
    end