Actually, taking my own advice about avoiding the @@ variable, this is  better:

class Top
  class << self
    def inherited subclass
      self.subclasses << subclass
    end
    def subclasses
      @subclasses ||=[]
    end
  end
end

class A < Top; end
class B < Top; end
Top.subclasses #=> [A,B]

class C < A; end
A.subclasses #=> [C]

#and if you wanted all classes to be able to track their subclasses:
class Class
  def inherited subclass
    subclasses << subclass
  end
  def subclasses
    @subclasses ||=[]
  end
end


Phil

On 1/3/06, Topher Cyll <[EMAIL PROTECTED]> wrote:
> Last login: Tue Jan  3 18:42:53 on ttyp1
> Welcome to Darwin!
> You have new mail.
> nomad:~ toph$ clear
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
> nomad:~ toph$ irb
> irb(main):001:0>
> irb(main):002:0*
> irb(main):003:0* class Foo
> irb(main):004:1>   @@foo = self
> irb(main):005:1> end
> => Foo
> irb(main):006:0>
> irb(main):007:0*
> irb(main):008:0* class Bar < foo
> irb(main):009:1>   def self.foo
> irb(main):010:2>     @@foo
> irb(main):011:2>   end
> irb(main):012:1> end
> NameError: undefined local variable or method `foo' for main:Object
>         from (irb):8
> irb(main):013:0> class Bar < Foo
> irb(main):014:1>   def self.foo
> irb(main):015:2>     @@foo
> irb(main):016:2>   end
> irb(main):017:1> end
> => nil
> irb(main):018:0> Bar.foo
> => Foo
> irb(main):019:0>
> irb(main):020:0*
> irb(main):021:0* class Foo
> irb(main):022:1>   class << self
> irb(main):023:2>     attr_accessor :baz
> irb(main):024:2>   end
> irb(main):025:1> end
> => nil
> irb(main):026:0>
> irb(main):027:0*
> irb(main):028:0*
> irb(main):029:0*
> irb(main):030:0*
> irb(main):031:0*
> irb(main):032:0*
> irb(main):033:0*
> irb(main):034:0*
> irb(main):035:0*
> irb(main):036:0*
> irb(main):037:0*
> irb(main):038:0* Foo.baz
> => nil
> irb(main):039:0> Foo.baz = "baz"
> => "baz"
> irb(main):040:0> Foo.baz
> => "baz"
> irb(main):041:0> class C < foo
> irb(main):042:1> end
> NameError: undefined local variable or method `foo' for main:Object
>         from (irb):41
> irb(main):043:0> class C < Foo
> irb(main):044:1>  end
> => nil
> irb(main):045:0> C.baz
> => nil
> irb(main):046:0> C.baz = "foo"
> => "foo"
> irb(main):047:0> C.baz
> => "foo"
> irb(main):048:0> Foo.baz
> => "baz"
> irb(main):049:0>
> irb(main):050:0*
> irb(main):051:0* Object.baz
> NoMethodError: undefined method `baz' for Object:Class
>         from (irb):51
> irb(main):052:0>
> irb(main):053:0*
> irb(main):054:0*
> irb(main):055:0*
> irb(main):056:0*
> irb(main):057:0* module X
> irb(main):058:1>
> irb(main):059:1*  def self.included mod
> irb(main):060:2>    mod.extend ClassMethods
> irb(main):061:2>  end
> irb(main):062:1>  module ClassMethods
> irb(main):063:2>    def x
> irb(main):064:3>    end
> irb(main):065:2>    def list
> irb(main):066:3>      @list ||= []
> irb(main):067:3>    end
> irb(main):068:2>  end
> irb(main):069:1> end
> => nil
> irb(main):070:0>
> irb(main):071:0*
> irb(main):072:0* class Z
> irb(main):073:1>   include X
> irb(main):074:1> end
> => Z
> irb(main):075:0> Z.list
> => []
> irb(main):076:0>
> irb(main):077:0* module X
> irb(main):078:1>   def self.included mod
> irb(main):079:2>     puts "#{self} has been included in #{mod}"
> irb(main):080:2>     mod.extend ClassMethods
> irb(main):081:2>   end
> irb(main):082:1> end
> => nil
> irb(main):083:0> class Y
> irb(main):084:1>   include X
> irb(main):085:1> end
> X has been included in Y
> => Y
> irb(main):086:0> module X
> irb(main):087:1>   def self.something
> irb(main):088:2>     "something"
> irb(main):089:2>   end
> irb(main):090:1> end
> => nil
> irb(main):091:0> Y.something
> NoMethodError: undefined method `something' for Y:Class
>         from (irb):91
> irb(main):092:0> X.something
> => "something"
> irb(main):093:0> class Xyz
> irb(main):094:1>   include X
> irb(main):095:1> end
> X has been included in Xyz
> => Xyz
> irb(main):096:0> Xyz.something
> NoMethodError: undefined method `something' for Xyz:Class
>         from (irb):96
> irb(main):097:0>
> irb(main):098:0*
> irb(main):099:0*
> irb(main):100:0*
> irb(main):101:0* exit
> nomad:~ toph$ irb
> irb(main):001:0> module X
> irb(main):002:1>   def self.included mod
> irb(main):003:2>     puts "#{self} is included in #{mod}"
> irb(main):004:2>     mod.extend ClassMethods
> irb(main):005:2>   end
> irb(main):006:1>
> irb(main):007:1*   module ClassMethods
> irb(main):008:2>   end
> irb(main):009:1> end
> => nil
> irb(main):010:0>
> irb(main):011:0*
> irb(main):012:0* class Foo
> irb(main):013:1>   @@subclasses = []
> irb(main):014:1>   def self.inherited subclass
> irb(main):015:2>     @@subclasses << subclass
> irb(main):016:2>   end
> irb(main):017:1>   def self.subclasses
> irb(main):018:2>     @@subclasses
> irb(main):019:2>   end
> irb(main):020:1> end
> => nil
> irb(main):021:0> class Bar < Foo
> irb(main):022:1> end
> => nil
> irb(main):023:0> Bar.subclasses
> => [Bar]
> irb(main):024:0> class Z < Foo
> irb(main):025:1> end
> => nil
> irb(main):026:0> Foo.subclasses
> => [Bar, Z]
> irb(main):027:0> Bar.subclasses
> => [Bar, Z]
> irb(main):028:0>
> _______________________________________________
> PDXRuby mailing list
> [email protected]
> IRC: #pdx.rb on irc.freenode.net
> http://lists.pdxruby.org/mailman/listinfo/pdxruby
>
_______________________________________________
PDXRuby mailing list
[email protected]
IRC: #pdx.rb on irc.freenode.net
http://lists.pdxruby.org/mailman/listinfo/pdxruby

Reply via email to