Attr_accessor weirdness, or something

Hi all! I’ve got a question, and I hope it can be answered. I’m
currently using attr_accessor to set up a list of variables that are
accessed throughout a class, and I’m running into trouble.

See, I’ve got something like the following:

class Test
attr_accessor :timer
def initialize
@timer = Time.now
end

def update_timer
timer = Time.now
end
end

But, as simple as it looks, it doesn’t work. I’ll make a new Test
object and call update_timer all I want, and it won’t update. It seems
a bit counter-intuitive. I’ve made an accessor for a variable that I
declare when initialized, and then go to change it, and it doesn’t
work.

However, if I change the ‘timer’ in update_timer to ‘@timer’, it works
perfectly fine. Why is this?

Thank you!

Change update_timer to:

def update_timer
self.timer = Time.now
end

Mark

On 1/20/07, CBlair1986 [email protected] wrote:

def update_timer
timer = Time.now

you are assigning to a local variable, as you found out yourself you
can
assign to the instance variable
@timer = Time.now
if you want to use the accessor method you have to write this as
self.timer = Time.now

end

end

But, as simple as it looks, it doesn’t work. I’ll make a new Test
object and call update_timer all I want, and it won’t update. It seems
a bit counter-intuitive. I’ve made an accessor for a variable that I
declare when initialized, and then go to change it, and it doesn’t
work.

However, if I change the ‘timer’ in update_timer to ‘@timer’, it works
perfectly fine. Why is this?

This is a trap lots of folks falls in, Ruby just prefers autocreation of
local variables
to method resolution.

HTH
Robert

Thank you!

CBlair1986 wrote:

end
work.

However, if I change the ‘timer’ in update_timer to ‘@timer’, it works
perfectly fine. Why is this?

Thank you!

@timer is an instance variable; timer isn’t.

CBlair1986 wrote:

def update_timer
timer = Time.now
end

Ruby can’t tell if you mean:
a) Call the method named “timer=” and pass it the value of Time.now, or
b) Set the local variable named “timer” to the value of Time.now.

It chooses the latter interpretation, when you meant the former. To
help the interpretter out, write that as:
self.timer = Time.now
instead. (This is slightly better, though slightly slower, than
directly accessing the instance variable, in case you alter want to
change what happens in your time= setter method.)

Phrogz wrote:

help the interpretter out, write that as:
self.timer = Time.now
instead. (This is slightly better, though slightly slower, than
directly accessing the instance variable, in case you alter want to
change what happens in your time= setter method.)

Thank you, Phrogz! Thinking on it now, it’s obvious. Must’ve had a late
night, I guess.

Thanks again, all!