Ruby/Rails:了解ruby getter-setter方法和实例

BC0*_*C00 1 ruby ruby-on-rails getter-setter ruby-on-rails-3

我是ruby和编程的新手,我正在尝试掌握一些关键概念.鉴于我有一类狗,具有以下特点.

class Dog
  attr_accessor :type, :popularity, :total

  def initialize(type = nil)
    @type = type
  end

  def total_dogs
    Dog.count
  end

  def total
    Dog.where(:type => self.type).size
  end

  def popularity
    total.to_f/total_dogs
  end
end
Run Code Online (Sandbox Code Playgroud)

我想要了解的是,ruby如何通过getter/setter方法将属性持久化到实例.我清楚地知道,如果我实例化一个新实例然后将属性保存到该实例,那么这些属性就绑定到该实例,因为如果我查看该对象,则属性如下所示:

 @dog = Dog.new
 @dog
 => #<Dog:0x007fa8689ea238 @type=nil> 
Run Code Online (Sandbox Code Playgroud)

我很容易理解,当我传递@dog对象时,总是将@type属性作为nil.但是,我理解的情况是我将这个@dog对象传递给另一个类.就像我做的那样:

 Owner.new(@dog)
Run Code Online (Sandbox Code Playgroud)

当我在所有者类中并且我调用@ dog.popularity时,它如何知道该实例的流行度值?在运行时,所有方法都被处理,然后该实例总是与当时的值绑定?抱歉,如果这没有意义,或者我离开了.

Nei*_*ter 6

当你这样做

@dog = Dog.new
Run Code Online (Sandbox Code Playgroud)

你做了两件特别的事情

1)为代码当前所在的任何对象创建一个实例变量@dog

2)实例化Dog的新实例(包含其所有方法和属性)并将其引用分配给@dog

@dog是一个变量,恰好指向你在那时创建的Dog实例("类的实例",通常意思是"对象").您可以将其他变量设置为指向同一个实例,而在Ruby中,这通常是您传递数据的方式.对象包含实例变量,这些实例变量指向更多对象.

使用赋值运算符(即"="),您可以将变量指向任何其他对象.

要依次回答您的问题:

当我在所有者类中并且我调用@ dog.popularity时,它如何知道该实例的流行度值?

您必须小心使用Ruby(以及一般的OO语言)来区分描述和问题中的类和对象.Ruby我假设您指的是Owner类中的一行代码,并且您打算使用所有者对象.我还假设@dog是您添加到所有者的属性.

在这种情况下,Ruby知道因为@dog指向您添加到所有者的Dog对象.每个Dog对象都有自己的所有Dog实例变量的副本.你确实需要在Ruby中小心,因为变量指向对象,你不是简单地将同一个Dog对象传递给所有的所有者(即它们都有效地共享一只狗).因此,您需要了解何时创建新实例(通过新实例)以及何时只是处理现有引用.

在运行时,所有方法都被处理,然后该实例总是与当时的值绑定?

不可以.在运行时,基本的Ruby只会执行您编码的分配.在分配了分配它们的代码之前,实例变量甚至可能不存在.如果你使用attr_reader等方法,那么变量至少会存在(但除非你在初始化期间分配一些东西,否则它们将是nil)