上下文:我目前正在使用parser gem,并试图处理什么是公共方法的所有情况。
我已经编写了下一个代码,希望它在运行时失败。但事实并非如此。
class Foo
class << self
def self.met
puts "I'm just a troll"
end
class << self
def mut
puts "Try and find me"
end
end
end
end
所以我想知道met
在哪里可调用(Foo.met
会引发NoMethodError
)吗?这是有用的Ruby模式还是只是我不应该做的事,也不在乎?
答案 0 :(得分:5)
Ruby中的每个对象都有自己的singleton class。在这里定义了所有实例方法。
请考虑以下示例。
class C; end
c1, c2 = C.new, C.new
c1.extend(Module.new { def m1; 42; end })
c1.m1
#⇒ 42
c2.m1
#⇒ NoMethodError: undefined method `m1' for #<C:0x000055cb062e6888>
c1.singleton_class.instance_methods.grep /m1/
#⇒ [:m1]
c2.singleton_class.instance_methods.grep /m1/
#⇒ []
需要Singleton类来扩展对象等。
在Ruby中,一切都是对象。类确实也是对象。这就是每个班级都有自己的单例班级的原因。每个单例类都有其单例类。
c1.singleton_class.singleton_class.singleton_class.singleton_class
#⇒ #<Class:#<Class:#<Class:#<Class:#<C:0x000055cb0459c700>>>>>
在foo
上定义的方法存储在foo
的单例类中。在foo
的单例类中定义的方法存储在foo
的单例类的singleton类中。依此类推。
虽然不太实用,但由于Ruby如何将所有内容都视为Object
,因此仍然有可能。