From: Nasir Khan Date: 2007-04-04T00:39:19+09:00 Subject: Re: Find the fully qualified name of a class from a string ------=_Part_8616_21970501.1175614724022 Content-Type: text/plain; charset=ISO-8859-1; format=flowed Content-Transfer-Encoding: 7bit Content-Disposition: inline Good. This is better. Thanks ~nasir On 4/2/07, Rick DeNatale wrote: > > On 3/31/07, Nasir Khan wrote: > > Here is an abridged (out of context) version of my original solution. > (which > > I am using now) > > ----- > > nasir@sparkle:misc>cat find_class_name.rb > > > > module EmptyModule > > def EmptyModule.clear_all > > constants.each {|x| remove_const(x.to_sym)} > > end > > end > > > > @my_classes = [] > > > > def class_from_string(str) > > EmptyModule.clear_all # clean the slate > > EmptyModule.module_eval(str) > > end > > > > cstr = < > module B > > class A > > def a > > puts "hello" > > end > > end > > end > > module B > > class C > > end > > class D > > end > > end > > EOF > > > > # This string will usually come from some external invocation of this > > function > > > > class_from_string(cstr) > > > > > > def find_class mod > > mod.constants.each do |str| > > m = mod.const_get(str) > > if m.class == Module > > find_class(m) > > else > > cname = m.to_s > > cname = cname.match(/EmptyModule::/).post_match > > @my_classes << cname > > end > > end > > end > > > > > > find_class( EmptyModule ) > > puts @my_classes.uniq > > > > --------------- > > > > And the result - > > > > nasir@sparkle:misc>ruby find_class_name.rb > > B::D > > B::C > > B::A > > > > ---------------- > > > > I guess I will stick with this solution. set_trace_func usage is very > > interesting but as I could have potentially several such evaluations > going > > on in parallel, I would go with the solution above. > > > > Comments criticisms welcome. > > This is still not thread safe since if you are doing this on two > different threads they are sharing the EmptyModule. > > Here's my variation using your approach but with an anonymous module > to do the module_eval: > > rick@frodo:/public/rubyscripts$ cat find_classes2.rb > class String > def all_class_names > mod = Module.new > mod.module_eval(self) > mod.all_class_names > end > end > > class Module > def all_class_names > class_names = [] > constants.each do |const_name| > const = const_get(const_name) > case const > when Class > class_names << const.to_s.split(/::/,2)[1] > when Module > class_names += const.all_class_names > end > end > class_names.uniq > end > end > > cstr = < module B > class A > def a > puts "hello" > end > end > end > > module B > class C > end > class D > end > > NonClassConst = :non_class_const > end > EOF > > puts cstr.all_class_names > rick@frodo:/public/rubyscripts$ ruby find_classes2.rb > B::C > B::A > B::D > > > > -- > Rick DeNatale > > My blog on Ruby > http://talklikeaduck.denhaven2.com/ > > ------=_Part_8616_21970501.1175614724022--