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 <CBlair1986@gmail.com> wrote:

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!

--
Mark Van Holstyn
mvanholstyn@gmail.com
http://lotswholetime.com

<snip>

  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!

···

On 1/20/07, CBlair1986 <CBlair1986@gmail.com> wrote:

--
"The best way to predict the future is to invent it."
- Alan Kay

CBlair1986 wrote:

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!

@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:

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.)

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

Thanks again, all!