Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/shell/5.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Ruby 如何传递send方法的所有参数 问题_Ruby - Fatal编程技术网

Ruby 如何传递send方法的所有参数 问题

Ruby 如何传递send方法的所有参数 问题,ruby,Ruby,在一个方法中,如何将作为发送方法的一部分提供的所有参数传递给另一个发送方法?所有参数的命名都应该考虑到没有像*args这样的占位符/捕捉器,但它们可以是关键字参数和非关键字参数的组合。此外,内部方法send不是super 示例(伪代码) def some_方法(一个_参数,一个名为_参数:) …做点什么。。。 某些\u其他\u方法([使用原始参数发送]) …做点别的。。。 终止 相关问题 7年前被问过 丑陋的黑客 根据我的发现,可以对关键字参数执行如下操作: def some_method(a

在一个方法中,如何将作为发送方法的一部分提供的所有参数传递给另一个发送方法?所有参数的命名都应该考虑到没有像
*args
这样的占位符/捕捉器,但它们可以是关键字参数和非关键字参数的组合。此外,内部方法send不是
super

示例(伪代码)
def some_方法(一个_参数,一个名为_参数:)
…做点什么。。。
某些\u其他\u方法([使用原始参数发送])
…做点别的。。。
终止
相关问题 7年前被问过

丑陋的黑客 根据我的发现,可以对关键字参数执行如下操作:

def some_method(a_named_parameter:, another_named_parameter:)
  ...do something...

  params = method(__method__)
           .parameters
           .map { |p| [p[1], binding.local_variable_get(p[1])] }
           .to_h

  some_other_method(**params)
  ...do something else...
end
def some_method(a_named_parameter, another_named_parameter)
  ...do something...

  params = method(__method__)
           .parameters
           .map { |p| binding.local_variable_get(p[1]) }

  some_other_method(*params)
  ...do something else...
end
对于非关键字参数:

def some_method(a_named_parameter:, another_named_parameter:)
  ...do something...

  params = method(__method__)
           .parameters
           .map { |p| [p[1], binding.local_variable_get(p[1])] }
           .to_h

  some_other_method(**params)
  ...do something else...
end
def some_method(a_named_parameter, another_named_parameter)
  ...do something...

  params = method(__method__)
           .parameters
           .map { |p| binding.local_variable_get(p[1]) }

  some_other_method(*params)
  ...do something else...
end
根据
方法(\uuu method\uuu)返回的信息。参数
也可以找到一个对这两种方法都有效的解决方案,但即使可以将所有这些都提取到一个助手中,这也是一种复杂的方法。

也许你的意思是这样的

def some_method *args, **kwargs, &block
  ...
  some_other_method(*args, **kwargs, &block)
  ...
end
但是我认为在
一些其他方法上使用方法委托更干净

也许你的意思是这样的

def some_method *args, **kwargs, &block
  ...
  some_other_method(*args, **kwargs, &block)
  ...
end

但我认为在
某些其他方法上使用方法委派更为简洁,只是出于好奇,您可能需要以下帮助:


出于好奇,您可能需要以下帮助:


这是一个非常有趣的问题,所以首先,谢谢你

假设
Binding
是一个对象,与其他任何对象一样,我们可以构建一个类来提供这种类型的功能,并利用原始方法的绑定将所有参数委托给下一个方法,如下所示:

class ArgsBuilder 
  attr_reader
  def initialize(b)
    @standard_args, @kwargs = [],{}
    @binding = b
    build!
  end
  def delegate(m)
    @binding.receiver.send(m,*@standard_args,**@kwargs,&@block)
  end
  private
    def build!
      set_block(&@binding.eval('Proc.new')) if @binding.eval('block_given?')
      @binding.eval('method(__method__)') 
        .parameters.each do |type,name|
          next if type == :block
          val = @binding.local_variable_get(name)
          if type =~ /key/
            @kwargs.merge!(type == :keyrest ? val : {name => val})
          else  
            type == :rest ? @standard_args.concat(val) : @standard_args << val
          end
        end
    end
    def set_block(&block)
      @block = block
    end
end
似乎很简单,可以作为一个助手,处理通过方法传递的命名块和匿名块

TL;DR

这显然需要在委托方法中匹配或至少接受类似签名,类似于
super
的工作方式。然而,我们可以进一步采取这一步骤,为参数类型创建类
[:req,:opt,:rest,:keyreq,:key,:keyrest,:block]
将它们放入一个集合中,然后询问委托给它们的方法,以确定要通过的正确参数;然而,我不确定这种类型的例子是否适合SO职位

附加说明:因为
buildinitialize
中调用code>,局部变量绑定在
ArgsBuilder
类的实例化点是静态的。e、 g

 def foo(n) 
   builder = ArgsBuilder.new(binding) 
   n = 17
   builder.delegate(:bar)
 end 
 def bar(n) 
   n 
 end 

  foo(42) 
  #=> 42
然而

 def foo(n) 
   n = 17
   ArgsBuilder.new(binding).delegate(:bar)
 end 

 foo(42) 
 #=> 17
这并不意味着可变对象无法更改

 def foo(n)
   builder = ArgsBuilder.new(binding) 
   n.upcase!
   builder.delegate(:bar)
 end

 foo('a')
 #=> "A"

显然,您可以通过将调用移动到
build

这是一个非常有趣的问题,所以首先,谢谢你

假设
Binding
是一个对象,与其他任何对象一样,我们可以构建一个类来提供这种类型的功能,并利用原始方法的绑定将所有参数委托给下一个方法,如下所示:

class ArgsBuilder 
  attr_reader
  def initialize(b)
    @standard_args, @kwargs = [],{}
    @binding = b
    build!
  end
  def delegate(m)
    @binding.receiver.send(m,*@standard_args,**@kwargs,&@block)
  end
  private
    def build!
      set_block(&@binding.eval('Proc.new')) if @binding.eval('block_given?')
      @binding.eval('method(__method__)') 
        .parameters.each do |type,name|
          next if type == :block
          val = @binding.local_variable_get(name)
          if type =~ /key/
            @kwargs.merge!(type == :keyrest ? val : {name => val})
          else  
            type == :rest ? @standard_args.concat(val) : @standard_args << val
          end
        end
    end
    def set_block(&block)
      @block = block
    end
end
似乎很简单,可以作为一个助手,处理通过方法传递的命名块和匿名块

TL;DR

这显然需要在委托方法中匹配或至少接受类似签名,类似于
super
的工作方式。然而,我们可以进一步采取这一步骤,为参数类型创建类
[:req,:opt,:rest,:keyreq,:key,:keyrest,:block]
将它们放入一个集合中,然后询问委托给它们的方法,以确定要通过的正确参数;然而,我不确定这种类型的例子是否适合SO职位

附加说明:因为
buildinitialize
中调用code>,局部变量绑定在
ArgsBuilder
类的实例化点是静态的。e、 g

 def foo(n) 
   builder = ArgsBuilder.new(binding) 
   n = 17
   builder.delegate(:bar)
 end 
 def bar(n) 
   n 
 end 

  foo(42) 
  #=> 42
然而

 def foo(n) 
   n = 17
   ArgsBuilder.new(binding).delegate(:bar)
 end 

 foo(42) 
 #=> 17
这并不意味着可变对象无法更改

 def foo(n)
   builder = ArgsBuilder.new(binding) 
   n.upcase!
   builder.delegate(:bar)
 end

 foo('a')
 #=> "A"

显然,您可以通过将调用移动到
build

我不明白,你知道一些其他方法的签名。为什么不简单地写出它需要的所有参数呢?它简单易读,不需要魔法。当然是@SergioTulentsev,我通常也会这么做。但是考虑到调用
super
是可能的,而且我发现这非常方便,我想知道一般来说是否也可以这样做。我希望它不像黑客那样神奇。我明白了。我希望你能找到:)@SergioTulentsev我欢迎你对我的答案提出意见,因为我正在努力寻找我可能遗漏的边缘案例。我不明白,你知道
某些其他方法的签名。为什么不简单地写出它需要的所有参数呢?它简单易读,不需要魔法。当然是@SergioTulentsev,我通常也会这么做。但是考虑到调用
super
是可能的,而且我发现这非常方便,我想知道一般来说是否也可以这样做。我希望它不像黑客那样神奇。我明白了。我希望您能找到:)@SergioTulentsev我欢迎您对我的答案的输入,因为我正在尝试查找我可能遗漏的边缘案例。除了我们在
某些方法的签名中丢失了所需的args/kwargs之外。@SergioTulentsev如果它们被修复,我们可以将它们塞进两个方法的签名中。是这样吗?事实上,我对这个问题并不确定。我想,这就是问题所在:“但是,考虑到打电话给super是可能的,而且我觉得非常方便,我想知道一般来说是否也可能。”。只对不相关的方法执行
super
所做的操作。除了在
某些方法的签名中丢失所需的args/kwargs之外。@SergioTulentsev如果它们是固定的,我们可以将它们塞进两个方法的签名中。是这样吗?我其实不太清楚