如何从单例方法访问实例变量?
class Test
def initialize(a)
@a = a
end
def item
item = "hola"
def item.singl
[self, @a].join(" + ")
end
item
end
end
test = Test.new("cao")
item = test.item
item.singl
#=> ... @a is nil
最佳答案
尝试使用 define_method。 Def 将您置于一个新的范围内。
class Test
def initialize(a)
@a = a
end
def item
item = "hola"
item.singleton_class.send(:define_method, :singl) do
[self, @a].join(" + ")
end
item
end
end
test = Test.new("cao")
item = test.item
item.singl #=> "hola + "
但在您的示例中,您仍然有一个问题,在字符串@a 的单例类中尚未定义。这主要是因为 self 在此上下文中是字符串实例,而不是 @a
存在的测试实例。要解决此问题,您可以将实例变量重新绑定(bind)到其他内容,但这可能不是您要寻找的行为。您还可以在新的单例类中设置实例变量。
例如,
重新绑定(bind)变量
class Test
def initialize(a)
@a = a
end
def item
item = "hola"
new_self = self
item.singleton_class.send(:define_method, :singl) do
[self, new_self.instance_variable_get(:@a)].join(" + ")
end
item
end
end
test = Test.new("cao")
item = test.item
item.singl
设置实例字符串变量
class Test
def initialize(a)
@a = a
end
def item
item = "hola"
item.singleton_class.send(:define_method, :singl) do
[self, @a].join(" + ")
end
item.singleton_class.send(:define_method, :set) do
@a = "cao"
end
item
end
end
test = Test.new("cao")
item = test.item
item.set
item.singl
重要的是要注意这两种方法之间的差异。在第一种方法中,我们通过原始对象保留对原始实例变量的引用。在第二种方法中,我们创建一个新的实例变量,绑定(bind)在新的单例类下,包含原始测试的副本。@a。
如果您使用的是非 native 对象,则可以混合使用这两种方法。通过指针使用单例类新实例变量引用旧实例变量的对象,但这不适用于 int、string、float 等...
编辑:正如 Benoit 所指出的,在第二种方法中,“set”方法应该只是一个 attr_accessor。事实上,您完全可以在不定义新方法的情况下设置实例变量。通过 item.instance_variable_set(:@, "cao")
关于ruby - 从单例方法访问实例变量,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/7926642/