Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

Dynamic object construction

0 views
Skip to first unread message

John Lam

unread,
Apr 18, 2005, 11:09:46 PM4/18/05
to
I'm trying to create a new object where the class of the object is
parameterized. My current solution is to use eval():

def create(class)

@obj = eval("#{class}.new()")

end

Is there a better way of doing this to avoid the hit of eval()?

Thanks,

-John

http://www.iunknown.com

Bill Atkins

unread,
Apr 18, 2005, 11:24:28 PM4/18/05
to
If class is a a class name (a String):

@obj = Object.const_get(klass).new

Using "class" as a parameter name won't work - the standard is to use
"klass" instead.

Bill


--
Bill Atkins

John Lam

unread,
Apr 18, 2005, 11:33:09 PM4/18/05
to
Thanks guys! const_get() works like a charm.

My fault for typing class as the parameter name - that's what I get for
typing code frags from scratch without running them first in a language
I've been using for 12 hours :)

-John
http://www.iunknown.com

David Heinemeier Hansson

unread,
Apr 19, 2005, 6:46:10 AM4/19/05
to
> Thanks guys! const_get() works like a charm.

If you're working with Rails, or just have the Active Support gem
available, this pattern has been boiled down to
klass.constantize.new().
--
David Heinemeier Hansson,
http://www.basecamphq.com/ -- Web-based Project Management
http://www.rubyonrails.org/ -- Web-application framework for Ruby
http://www.loudthinking.com/ -- Broadcasting Brain

George Moschovitis

unread,
Apr 20, 2005, 2:57:25 AM4/20/05
to
> @obj = Object.const_get(klass).new

does this work if klass == My::Namespace::Klass ?

-g.

Trans

unread,
Apr 20, 2005, 5:54:07 PM4/20/05
to

George Moschovitis wrote:
> > @obj = Object.const_get(klass).new
>
> does this work if klass == My::Namespace::Klass ?

Assuming you mean the string value

klass = "My::Namespace::Klass"

The answer is No. One has to do:

klass = "Klass"
@obj = My::Namespace.const_get(klass).new

The namespace issue is problematic. One alternative is in Ruby Facets:

require 'facet/object/constant'

klass == "My::Namespace::Klass"

@obj = constant(klass).new

T.

George Moschovitis

unread,
Apr 21, 2005, 9:02:07 AM4/21/05
to
> The answer is No. One has to do:
> klass = "Klass"
> @obj = My::Namespace.const_get(klass).new

I was expecting the negative answer ;-)

> One alternative is in Ruby Facets

Interesting, I 'll see how that works...

-g.

Nicholas Seckar

unread,
Apr 21, 2005, 12:01:53 PM4/21/05
to
On 4/20/05, Trans <tran...@gmail.com> wrote:
> Assuming you mean the string value
> klass = "My::Namespace::Klass"
> The answer is No. One has to do...

Or the ever popular

klass.split('::').inject(Object) {|parent, name| parent.const_get(name)}

0 new messages