在Ruby中,如何检查方法"foo =()"是否已定义?

Ale*_*ert 73 ruby syntax-error

在Ruby中,我可以定义一个方法foo =(bar):

irb(main):001:0> def foo=(bar)
irb(main):002:1>   p "foo=#{bar}"
irb(main):003:1> end
=> nil
Run Code Online (Sandbox Code Playgroud)

现在我想检查它是否已定义,

irb(main):004:0> defined?(foo=)
SyntaxError: compile error
(irb):4: syntax error, unexpected ')'
 from (irb):4
 from :0
Run Code Online (Sandbox Code Playgroud)

在这里使用的正确语法是什么?我假设必须有一种方法来逃避"foo =",以便它被解析并正确传递给定义的?运营商.

mol*_*olf 122

问题是该foo=方法旨在用于分配.您可以通过defined?以下方式查看正在发生的事情:

defined? self.foo=()
#=> nil
defined? self.foo = "bar"
#=> nil

def foo=(bar)
end

defined? self.foo=()
#=> "assignment"
defined? self.foo = "bar"
#=> "assignment"
Run Code Online (Sandbox Code Playgroud)

比较一下:

def foo
end

defined? foo
#=> "method"
Run Code Online (Sandbox Code Playgroud)

要测试是否foo=定义了方法,您应该使用respond_to?:

respond_to? :foo=
#=> false

def foo=(bar)
end

respond_to? :foo=
#=> true
Run Code Online (Sandbox Code Playgroud)


The*_*heo 36

您可以使用该respond_to?方法检查方法是否存在,并向其传递符号,例如,bar.respond_to?(:foo=)以查看对象bar是否具有方法foo=.如果您想知道类的实例是否响应您可以method_defined?在类(或模块)上使用的方法,例如Foo.method_defined?(:bar=).

defined?不是方法,而是返回操作数描述的运算符(如果未定义,则为nil,这就是为什么它可以在if语句中使用).操作数可以是任何表达式,即常量,变量,赋值,方法,方法调用等.当你这样做时它不起作用的原因defined?(foo=)是因为括号,跳过它们它应该更多或者更少的预期.话虽这么说,defined?是一个非常奇怪的运算符,没有人用它来测试方法的存在.

  • 啊,Ruby核心库的拼写......`respond_to?`,`start_with?`,`end_with?`. (3认同)
  • http://stackoverflow.com/questions/5280556/why-does-ruby-use-respond-to-instead-of-responds-to 对命名 TL 背后的选择有很好的解释;DR `you.knock if you .respond_to?(:knock)` (3认同)