I’m new to Ruby and confused about how I can make a method in Class similar to :attr_accessor, in that it adds methods to a user class, but so these added methods have access to a pre-initialized instance variable. It’s difficult for me to explain so here is a greatly simplified sample of my efforts:
class Class
def super_accessor_wow(attr_name)
attr_name = attr_name.to_s
new_var_name = "@crazy_var_name"
instance_variable_set(new_var_name, ["hi", "everyone"])
module_eval(%Q/
def super_#{attr_name}()
return @#{attr_name}
end
def super_#{attr_name}=(value)
@#{attr_name} = value
end
def greetings
return #{new_var_name}
end
/)
end
end
This is how I’m trying to use the new method on Class to modify my own class:
class Foo
super_accessor_wow(:bar)
end
foo1 = Foo.new()
foo1.super_bar = 1000
puts foo1.super_bar
puts foo1.greetings.inspect
The first puts prints '1000'
The second puts prints 'nil', so my instance_variable_set call in super_accessor_wow seemingly has no effect.
I expected that the second puts would print '['hi', 'everyone']' by the way. All of this code is contained in a single Ruby file.
Your
instance_variable_setis called when you callsuper_accessor_wowduring the class definition. No instance of the class exists yet. You create an instance of the class when you callnew. You could add your@crazy_var_nameinitialization to the constructor, or you could define it in thegreetingsmethod:Put the default in a class variable, and initialize the instance variable in the constructor (be aware that this creates a constructor for your class, and if you then create your own constructor, it will override this one):
Outputs:
Define it in the
greetingsmethod:Outputs