有没有办法知道方法需要多少参数?

时间:2013-07-11 09:41:25

标签: ruby

使用irb,我们可以通过以下方式列出特定对象的方法:

"Name".methods

但是如果我想知道特定方法需要多少参数,我该如何实现呢?我的意思是有什么办法(通过在irb上点击一些命令),我们可以获得特定方法的参数数量(而不是引用文档)?

.methods仅返回方法名称,而不返回方法的参数列表。

3 个答案:

答案 0 :(得分:37)

您可以使用方法Method#arity

"string".method(:strip).arity
# => 0

来自Ruby文档:

  

返回方法接受的参数数量的指示。   对于采用固定数量的方法,返回非负整数   参数。对于采用可变数量参数的Ruby方法,   返回-n-1,其中n是所需参数的数量。对于方法   用C语言编写,如果调用采用变量数,则返回-1   参数。

所以,例如:

# Variable number of arguments, one is required
def foo(a, *b); end
method(:foo).arity
# => -2

# Variable number of arguments, none required
def bar(*a); end
method(:bar).arity
# => -1

# Accepts no argument, implemented in C
"0".method(:to_f).arity
# => 0

# Variable number of arguments (0 or 1), implemented in C
"0".method(:to_i).arity
# => -1


更新我刚刚发现了Method#parameters的退出,它可能非常有用:

def foo(a, *b); end
method(:foo).parameters
# => [[:req, :a], [:rest, :b]] 

答案 1 :(得分:9)

您可以使用arity

  

返回方法接受的参数数量的指示。返回采用固定数量参数的方法的非负整数。对于采用可变数量参数的Ruby方法,返回-n-1,其中n是所需参数的数量。对于用C编写的方法,如果调用采用可变数量的参数,则返回-1。

来自ruby-doc

的示例
class C
  def one;    end
  def two(a); end
  def three(*a);  end
  def four(a, b); end
  def five(a, b, *c);    end
  def six(a, b, *c, &d); end
end

c = C.new
c.method(:one).arity     #=> 0 
c.method(:two).arity     #=> 1
c.method(:three).arity   #=> -1
c.method(:four).arity    #=> 2
c.method(:five).arity    #=> -3
c.method(:six).arity     #=> -3

答案 2 :(得分:0)

当您无法使用其他答案中定义的方法时,有一种特殊情况。它是关于某个还没有实例的类的方法 #initialize

如果您为 Method#arity 尝试 SomeClass::new,您将始终获得 -1:

class SomeClass
  def initialize(a, b)
  end
end
SomeClass.method(:new).arity # => -1
  

您需要类 SomeClass 的一个实例才能在其上使用 Method#arity,但您无法获得此实例,因为您还不知道需要 SomeClass::new 多少个参数。

幸运的是,这个问题可以解决。只需在 instance_method(:initialize) 上使用 SomeClass,您就会得到想要的结果:

class SomeClass
  def initialize(a, b)
  end
end
SomeClass.instance_method(:initialize).arity # => 2

顺便说一句,您可以将这种方法用于某个类的任何实例方法,而无需创建此类的实例。例如,以下两行将给出相同的结果:

"string".method(:strip).arity # => 0
String.instance_method(:strip).arity # => 0
相关问题