如何从其他模块访问模块的实例变量?

问题描述:

我模块如何从其他模块访问模块的实例变量?

module SomeModule 
    @param = 'Hello' 
end 

module Reporter 
    include SomeModule 
    def self.put 
    puts @param 
    end 
end 

当我打电话Reporter::put我没有得到任何输出,我想这Reporter模块有实例变量@param进不去。有没有办法从Reporter模块访问该变量?

+2

'self.put'是一个类级别的方法。你如何期望它访问实例变量? – mudasobwa

+0

你说得对,我在想什么? –

实例变量被称为例如变量,因为它们属于对象(又名 “实例”)。您的示例中有两个对象:SomeModuleReporter。两者都有自己的实例变量。 SomeModule有一个名为@param的实例变量,而Reporter有一个名为@param的实例变量。这两个实例变量是完全不相关的,即使它们具有相同的名称。想象一下混乱,如果每个对象都必须为实例变量提供自己的名字!

有什么办法从Reporter模块访问该变量吗?

不可以。您不能访问来自不同对象的实例变量。一个对象只能访问其自己的实例变量。

[注:它是可能使用反射当然(例如Object#instance_variable_getBasicObject#instance_eval,或BasicObject#instance_exec)。许多事情都可以使用反射。]

可以做,但是,是创建一个方法,让您访问读取该实例变量。这种方法被称为属性读者

module SomeModule 
    def self.param; @param end 
    @param = 'Hello' 
end 

module Reporter 
    def self.put 
    puts SomeModule.param 
    end 
end 

甚至还有自动为您生成这些方法的方法,它被称为Module#attr_reader

module SomeModule 
    class << self; attr_reader :param end 
    @param = 'Hello' 
end 

module Reporter 
    def self.put 
    puts SomeModule.param 
    end 
end 

如果你想也写实例变量,你也需要定义一个相应属性作家方法:

module SomeModule 
    class << self 
    attr_reader :param 

    private 

    def param=(param) 
     @param = param 
    end 
    end 

    self.param = 'Hello' 
end 

module Reporter 
    def self.put 
    puts SomeModule.param 
    end 
end 

还有一个名为Module#attr_writer的相应的方法,其生成用于您的属性写入方法:

module SomeModule 
    class << self 
    attr_reader :param 

    private 

    attr_writer :param 
    end 

    self.param = 'Hello' 
end 

module Reporter 
    def self.put 
    puts SomeModule.param 
    end 
end 
+0

非常感谢您提供这些信息,这对我来说非常有意义 –

您可以在此情况下

是使用类变量而不是instanse变量的

module SomeModule 
    @@param = 'Hello' 
end 

module Reporter 
include SomeModule 
def self.put 
    puts @@param 
end 
end 

Reporter.put打印123并返回nil

SomeModule.instance_variable_get(:@param)