Hi --

On Wed, 21 Sep 2005, HaPK wrote:

> Indeed, seems like a bug with constants assignment.
>
> class X
> A = 1
> end
>
> class Y < X
> A = 2
> end
>
> class Z < X
> end
>
> X.constants            => 'A'
> Y.constants            => 'A'
> Z.constants             => 'A'         # Z inherits constants from its parent
>
> X::A = 3
> Z::A                       => 3           # changes in superclass populated 
> to subclasses
>
> Z::A = 4
> X::A                      => 3           # changes in subclass remains local 
> to subclass
>
> Seems like assignments are made without lookup in superclasses.

There's no bug.  There's a lookup path for constants.  Z finds X::A on
its lookup path.  You could also do: Z::String and although you'd get
a warning, Ruby would indeed return the top-level constant String
(because there's no other String to replace it in the lookup path).

When you change X::A (aside from getting a warning :-) it's not
exactly that the change is propagated to Z.  Rather, the change
affects a constant that is on Z's lookup path -- so, naturally, when Z
sees that constant, it's changed.  It's not because Z is a subclass of
X.  The change to X::A would be visible from anywhere.

When you assign to Z::A, you're creating a new constant.  This has no
effect on X::A; the two are completely unrelated.


David

-- 
David A. Black
dblack / wobblini.net