从类外部访问实例变量

时间:2012-08-25 14:15:30

标签: ruby instance-variables

如果实例变量属于某个类,我可以直接使用类实例访问实例变量(例如@hello)吗?

class Hello
  def method1
    @hello = "pavan"
  end
end

h = Hello.new
puts h.method1

2 个答案:

答案 0 :(得分:129)

是的,您可以像这样使用instance_variable_get

class Hello
  def method1
    @hello = "pavan"
  end
end

h = Hello.new
p h.instance_variable_get(:@hello) #nil
p h.method1                        #"pavan" - initialization of @hello
p h.instance_variable_get(:@hello) #"pavan"

如果变量未定义(在我的示例中第一次调用instance_variable_get),则会得到nil


安德鲁在评论中提到:

  

您不应该将此作为访问实例变量的默认方式,因为它违反了封装。

更好的方法是定义一个访问者:

class Hello
  def method1
    @hello = "pavan"
  end
  attr_reader :hello  
end

h = Hello.new
p h.hello #nil
p h.method1                        #"pavan" - initialization of @hello
p h.hello #"pavan"

如果您想要其他方法名称,可以别名访问者:alias :my_hello :hello

如果您的代码中没有定义类,而是在gem中定义:您可以在代码中modify classesinsert new functions to classes

答案 1 :(得分:11)

您也可以通过这样调用attr_readerattr_accessor来完成此操作:

class Hello
  attr_reader :hello

  def initialize
    @hello = "pavan"
  end
end

class Hello
  attr_accessor :hello

  def initialize
    @hello = "pavan"
  end
end

调用attr_reader将为给定变量创建getter

h = Hello.new
p h.hello        #"pavan"

致电attr_accessor会为给定变量创建gettersetter

h = Hello.new
p h.hello        #"pavan"
h.hello = "John"
p h.hello        #"John"

根据您的理解,请相应地使用attr_readerattr_accessor。仅在您需要attr_accessorgetter时使用setter,并在仅需attr_reader时使用getter