当我这样做的时候有什么不同
class T
def initialize
self.class.class_eval do
def test
return self.class.object_id
end
end
end
end和
class T
def initialize
singleton_class.class_eval do
def test
return self.class.object_id
end
end
end
end谢谢
PS。Tass回答说,在本例中,singleton_class将为每个新对象返回不同的object_id,因为singleton_class只属于一个对象。但IRB显示下一步
1.9.2p180 :001 > class T
1.9.2p180 :002?>
1.9.2p180 :003 > def initialize
1.9.2p180 :004?> singleton_class.class_eval do
1.9.2p180 :005 > def test
1.9.2p180 :006?> return self.class.object_id
1.9.2p180 :007?> end
1.9.2p180 :008?> end
1.9.2p180 :009?> end
1.9.2p180 :010?>
1.9.2p180 :011 > end
=> nil
1.9.2p180 :012 > t = T.new
=> #<T:0x00000100ae9cb8>
1.9.2p180 :013 > t1 = T.new
=> #<T:0x00000100ad7ef0>
1.9.2p180 :014 > t1.test == t.test
=> true
1.9.2p180 :015 > t1.test
=> 2153233300
1.9.2p180 :016 > t.test
=> 2153233300
1.9.2p180 :017 > 发布于 2012-01-31 01:21:29
这些T类的实例之间的区别在于方法查找算法:总是在单例类(及其模块)中搜索方法,只有在此处找不到它时,才在类中搜索它。
这意味着如果我们在初始化后将方法test添加到类T的第一个实现中,我们将得到与对类T的第二个实现执行相同的结果:
# First example
class T
def initialize
self.class.class_eval do
def test
return self.class.object_id
end
end
end
end
t = T.new
class T
def test
'overriden'
end
end
puts t.test # => 'overriden'class T
def initialize
singleton_class.class_eval do
def test
return self.class.object_id
end
end
end
end
t = T.new
class T
def test
'overriden'
end
end
puts t.test # => 77697390发布于 2012-01-31 00:18:23
singleton_class为您提供了该对象唯一的Class。self.class为您提供了该Class的所有对象共享的类。Example
foobar = Array.new
# this defines a method on the singleton class
def foobar.size
"Hello World!"
end
foobar.size # => "Hello World!"
foobar.class # => Array
bizbat = Array.new
bizbat.size # => 0在上面的示例中,singleton_class将为每个新对象返回不同的object_id,因为一个singleton_class只属于一个Object。self.class将返回相同的值,因为self.class每次都指向相同的Class。
https://stackoverflow.com/questions/9066979
复制相似问题