无法从ruby中的类实例获取对象数据

时间:2014-05-15 15:14:07

标签: ruby oop

如何从我的班级实例中获取数据?我可以得到这个:

instance = MyModule::MyClass.new(obj1, obj2)

puts instance
#=> #<MyModule::MyClass:0x0000010120de68>

puts instance.inspect 
#=>  #<MyModule::MyClass:0x000001019157b0 @obj1=#<MyModule::MyOtherClass:0x00000101915b20 @obj=["stuff", "more stuff", "things"]>, @obj2=#<MyModule::MyThirdClass:0x00000101915a80 @obj=["more things", "even more"]>>

我以为我可以做instance.obj1并从中获取@obj数组。这给了我&#34;未定义的方法。&#34;这里有什么问题?

2 个答案:

答案 0 :(得分:2)

默认情况下,您无法从外部访问实例变量:

class Foo
  def initialize(obj)
    @obj = obj
  end
end

foo = Foo.new(123) #<Foo:0x007fdc312205f0 @obj=123>
foo.obj            # undefined method `obj' ... (NoMethodError)

您必须创建一个getter才能这样做,例如通过attr_reader

class Foo
  attr_reader :obj

  def initialize(obj)
    @obj = obj
  end
end

foo = Foo.new(123)
foo.obj            #=> 123

答案 1 :(得分:0)

你必须为我们发布你的类定义以确定问题是什么,但我猜你没有为你的对象定义属性getter / setter。由于Ruby变量作用域的工作方式,实例变量被本地化到对象实例的内部作用域(这意味着它们只能在类定义中的方法定义中访问)。

要从类定义范围之外访问这些变量,必须定义属性getter和setter,以及将这些变量公开给外部范围的方法:

class Foo
  def initialize(name)
    @name = name
  end

  # attribute getter for @name
  def name
    @name
  end

  # attribute setter for @name
  def name=(n)
    @name = n
  end
end

这是一种常见的模式,Ruby提供了帮助方法来定义实例变量的setter和getter:attr_readerattr_writerattr_accessor

  • attr_reader将一个或多个符号作为参数(对应于您希望定位的实例变量),并为每个符号创建 getter 方法。
  • attr_writer采用与attr_reader相同的符号列表,但为每个作为参数传递的实例变量名称创建 setter 方法
  • attr_accessor为名为的实例变量生成 setter getter 方法。
class Bar
  attr_reader :name   # only allow reading of @name
  attr_accessor :rank, :age  # enable both reading and writing of @rank and @age

  def initialize(name, rank, age)
    @name = name
    @rank = rank
    @age = age
  end
end

b = Bar.new('Jack BeLucky', 'Corporal', 32)
b.name
=> 'Jack BeLucky'
b.age 
=> 32
b.age += 1
b.age
=> 33