Calling Instance Variables without @

主宰稳场 提交于 2021-02-04 21:42:09

问题


I'm new to Ruby programming and I've seen a few examples now where an instance variable is being called without the "@" symbol in front of it.

I'm not sure if this because the method is being called and the instance variable is stored in the method as a result of a attr_reader in the class or if because I have the wrong understanding of instance variables.

Here's an example of what I'm referring to taken from Russ Olsen's Eloquent Ruby, where the @unique array has the size method called on it without the "@" symbol in front of it:

class TextCompressor
attr_reader :unique, :index

def initialize(text)
    @unique = []
    @index = []
    add_text(text)
end

def add_text(text)
    words = text.split
    words.each { |word| add_word(word) }
end

def add_word(word)
    i = unique_index_of(word) || add_unique_word(word)
    @index << i
end

def unique_index_of(word)
    @unique.index(word)
end

def add_unique_word(word)
    @unique << word
    unique.size - 1
end
end

回答1:


I'm also new to Ruby and have been learning for a couple weeks. I believe:

attr_reader :unique

is functionally identical to defining the method:

def unique
  @unique
end



回答2:


You don't "call" instance variables, but you call methods. Your assumption is right, that you do an actual method call without the "@". The attr_accessor :unique, :index is basically equivalent to:

def unique
  @unique
end

def unique=(val)
  @unique = val
end

def index
  @index
end

def index=(val)
  @index = val
end

That you can write unique = val when a unique=(val) method is defined is syntactic sugar provided by Ruby to make it look like a variable assignment, even though it's actually a method call.

In general you shouldn't mix the different ways of referencing the instance variable in one method though. If a method has to know the implementation details of how the value is stored, you can use the direct access with @. Otherwise, you should use the accessor methods. The less code is relying on implementation details, the better. Even if it's inside instance methods of the respective instance.




回答3:


attr_reader creates method with the name of the argument you supplied, returning a instance variable with same name. eg: -

attr_reader :name

it will create a method at runtime like this

  def name
    @name
  end

and same with attr_writer, it creates a setter method for that argument like

attr_writer :name

def name=(value)
  @name = value
end

and, attr_accessor creates both getter and setter with the name of the argument you supplied.




回答4:


The line :

attr_reader :unique, :index

creates getter methods for unique and index like :

def unique
 @unique
end

So when you call :

unique.size

It first calls the getter method which returns @unique and then size method on it.



来源:https://stackoverflow.com/questions/18502005/calling-instance-variables-without

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!