I’d just asked this not long ago - here’s a copy/paste of the
reponse
from David
Hi –
On Mon, 4 Sep 2006, Greg H wrote:
Had a quick look at this (e.g. cattr_reader - extract below) - still I
little unclear to me. Do you think you could run what “cattr_accessor”
does
in layman’s terms at all? e.g. difference between class & instant
aspects. (sorry - the penny hasn’t dropped yet )
In layman’s terms, I’d describe it as, “A computer programming thing”
But here’s a somewhat super-layman explanation.
Ruby has an attr_* family of methods:
class C
attr_accessor :x
attr_reader :y
attr_writer :z
end
These attr_* methods are meta-methods; that is, calling them actually
results in the automatic creation of other methods. In the example
above, instances of C will have the following methods:
x # reader
x= # writer
y # reader
z= # writer
The idea is to provide a convenient way to get and/or set state in an
object:
c = C.new
c.x = 1 # actually a call to the x= method!
puts c.x # a call to the x method
The way this works is that the reader and writer methods (x, x=, etc.)
store/retrieve values in/from instance variables. If you wrote them
out, the methods that the attr_* methods create for you would look
like this:
class C
def x # read “attribute” (i.e., value of instance variable)
@x
end
def x=(value) # set "attribute" (i.e., set instance variable)
@x = value
end
def y
@y
end
def z=(value)
@z = value
end
end
In addition to instance variables, Ruby has class variables. The
purpose of the cattr_* methods is to provide a mechanism exactly like
the above – but using class variables instead of instance variables.
Furthermore, the set/get operations are available both to instances of
the class, and to the class itself:
class D
cattr_accessor :a
end
d = D.new
d.a = 1 # set via an instance
puts D.a # get via the class
So it’s just a kind of elaboration of the original Ruby attribute
implementation. To get both the class and its instances to know about
the get and set methods, there have to be two of each. So this is
what the expanded version of the last example looks like:
class D
def self.a # class get method
@@a
end
def self.a=(value) # class set method
@@a = value
end
def a # instance get method
@@a
end
def a=(value) # instance set method
@@a = value
end
end
I personally consider “cattr” (class attribute) a misnomer.
“Attribute” suggests a property of an object. Class variables do not
map onto the state of any particular object; they are visible to a
given class, all of its subclasses, and all of the instances of itself
and those subclasses. So when you save a value in a class variable,
it’s a considerable stretch to refer to it as an “attribute”. But
anyway, the above is how it works and what it does.
David