了解公安121

时间:2015-01-08 15:36:31

标签: ruby

我正在研究Ruby koans(再次),我达到121(再次)。

我已经解决了,但有几件我不明白的事情。这是相关的公案代码:

def my_private_method
    "a secret"
  end
  private :my_private_method

  def test_calling_private_methods_without_receiver
    assert_equal "a secret", my_private_method
  end

  def test_calling_private_methods_with_an_explicit_receiver
    exception = assert_raise(NoMethodError) do
      self.my_private_method
    end
    assert_match /__/, exception.message
  end

事实证明,如果我在倒数第二行替换双下划线,它会经过my_private_method;所以exception.message是非方法名称的匹配,我猜。我也可以删除下划线,但我不认为这是课程的重点。

我认为self.my_private_method会抛出NoMethodError,并将其分配给异常。从另一个在线教程,我知道私有方法不能用self调用,所以我认为这就是重点。

但是,my_private_method似乎不是私密的,除非private :my_private_method这样做。那是怎么回事? (如果是这样的话,我会再次对Ruby的犹豫不决感到非常绝望,应该如何做,以及符号的能力,看似什么都可以。

所以,我的问题是:private :my_private_method做了什么?

3 个答案:

答案 0 :(得分:2)

符号什么都不做。它们只是数据。像字符串。或数字。方法做了些什么。特别是,private方法将方法设为私有。 attr_accessor方法创建了两种方法。等等。

  

所以,我的问题是:private :my_private_method做了什么?

它调用方法private传递:my_private_method作为参数。如果您查看private的文档,它会告诉您它使名称与私有符号匹配的方法。

答案 1 :(得分:2)

  

所以,我的问题是:private :my_private_method做了什么?

private实际上只是一种常规方法,在ModuleModule#private上定义。

来自the documentation for that method(强调我的):

  

privateself

     

private(symbol, ...)self

     

private(string, ...)self

     

如果没有参数,则设置后续的默认可见性   私有的定义方法。 使用参数,将命名方法设置为   具有私人可见性。字符串参数将转换为符号。

module Mod
  def a()  end
  def b()  end
  private
  def c()  end
  private :a
end
Mod.private_instance_methods   #=> [:a, :c]

答案 2 :(得分:0)

当你写:

class Foo
  def bar
    # some amazing things that bar does
  end
  private :bar
end

如果你愿意,那就是同样的事情:

class Foo

  private

  def bar
    # ...
  end
end

它的语法不同,效果相同。