From: ale@... Date: 2001-01-27T09:13:21+09:00 Subject: [ruby-talk:9967] Re: Dynamically instantiating a class (with a string) On Sat, 27 Jan 2001, Phil Tomson wrote: > I know I could (and probably should) do this with some kind of a factory > pattern... > > In Perl I can instantiate an object using a string that contains the name > of that object, like so: > > > $PLATFROM = "PC"; > $myPCTool = "Tool$PLATFORM"->new(blah...); > #later: > $PLATFORM = "UNIX"; > $myUnixTool = "Tool$PLATFORM"->new(blah...); > #where I have a class called ToolPC and another called ToolUNIX which > #inherit from Tool. > > I kind of like this capability, is there any way to do something like that > in Ruby? Hello Phil, I'd like to leave you with Dave's answer, but I don't like eval too much. So here's a way to find a class (searches breadth-first). There has been discussions about this before at ruby-talk (IIRC), but I was unable to find them with blade. Maybe someone can point our earlier discussions. - Aleksi module Kernel def get_class_for_name(name, objects = [Object]) return nil if objects.size == 0 object = objects.shift object.constants.each do |constant_name| real_object = object.const_get(constant_name) case real_object when Class return real_object if constant_name == name when Module objects << real_object end end return get_class_for_name(name, objects) end end klass = get_class_for_name("Fixnum") puts "#{klass} of type #{klass.type}" module Foo module Bar class Zak end end end klass = get_class_for_name("Zak") puts "#{klass} of type #{klass.type}" class ToolPC def identity puts "PC would suck, but luckily it runs unix" end end class ToolUNIX def identity puts "how come POSIX was never based on DOS?" end end for platform in ["PC", "UNIX"] myTool = get_class_for_name("Tool"+platform).new myTool.identity end