Forum: Ruby-core Sweet instance var assignment in the object initializer

Posted by boris_stitnicky (Boris Stitnicky) (Guest)
on 2012-12-09 05:31
(Received via mailing list)
Issue #5825 has been updated by boris_stitnicky (Boris Stitnicky).


Well... I like the sweetness... But to have such a feature working 
syntactically from
inside of #initialize method, but not from other methods... I don't 
know.

It's not like this is my suggestion, but since it is up for discussion, 
let me try to
straighten this proposal according to my own thinking:

These "attributes on steroids" are a thing to be done not at the level 
of the #initialize
method, but at the level of the module, along with #attr_accessor and 
friends.

Imho, it would be necessary to update #attr_accessor & friends to accept 
:autoinit
named argument:

attr_reader :name, :age, autoinit: true

Now there are two flavors of this candy, one with ordered arguments, one 
with named.
So we could have to specify it:

attr_reader :name, autoinit: :ordered
attr_reader :age, autoinit: :named

I'm sure you know what I mean here. Default option could be eg. :named.

Also, #autoinit method, or rather, #autoinit_named, #autoinit_ordered,
would have to be added to the Module, for those times, when we want to
autoinit, but don't want the reader/writer/accessor:

autoinit_named :age
autoinit_ordered :name

Afaik, current #attr_accessor & friends work by defining instance 
methods on
the module. How #autoinit should work, is a question. Two possibilities 
come
to my mind:

  1. By patching #initialize method.

  2. By creating and including a mixin patching #new class method, that 
would
     set the appropriate instance variables right after creating a new 
instance,
     in effect something like this:

     module AgeNamedArgAutoinit
       def new *args, &block
         named_args = args.extract_options!
         age = named_args.delete :age
         modified_args = args + named_args.empty? ? [] : [named_args]
         new_instance = super *modified_args, &block
         new_instance.instance_variable_set :@age, age
       end
     end

     module NameOrderedArgAutoinit
       def new *args, &block
         name = args.shift
         new_instance = super *args, &block
         new_instance.instance_variable_set :@name, name
       end
     end

     class MyClass
       include AgeNamedArgAutoinit
       include NameOrderedArgAutoinit
     end

Now MyClass.new( "John Smith", :whatever, age: 35, other_stuff: 
:whatever ) should
behave in the expected way.

Again, I have not come up with this proposal, I do not give +1 or -1 to 
it,
I am only trying to iron it to be more consistent, leaving the decision 
to others.
----------------------------------------
Feature #5825: Sweet instance var assignment in the object initializer
https://bugs.ruby-lang.org/issues/5825#change-34550

Author: goshakkk (Gosha Arinich)
Status: Assigned
Priority: Normal
Assignee: matz (Yukihiro Matsumoto)
Category:
Target version: next minor


I'm very excited about this feature in CoffeeScript, and think it might 
be a nice-to-have thing in Ruby 2.0.

That's how I think it would look like:

`class Me
  def initialize(@name, @age, @location); end
end`

So we can declare @variables in the initializer method parameters 
definition to avoid assigning instance variables from method arguments 
by hand, like:

`class Me
  def initialize(name, age, location)
    @name = name
    @age = age
    @location = location
  end
end`

Want to hear what do you guys think, does that feature worth being 
included in 2.0?
Please log in before posting. Registration is free and takes only a minute.
Existing account (Switch to SSL-encrypted connection)
NEW: Do you have a Google/GoogleMail or Yahoo account? No registration required!
Log in with Google account | Log in with Yahoo account
No account? Register here.