Question about accessing class-attributes.

Bjorn Pettersen BPettersen at NAREX.com
Mon Apr 28 19:05:06 EDT 2003


> From: Alex Martelli [mailto:aleax at aleax.it] 
> 
> Bjorn Pettersen wrote:
>    ...
> > Then define a hierarchy:
> > 
[...]
> >  class CountedPoint(Counted, Point):
> >      def __init__(self):
> >          super(CountedPoint.self).__init__(self)
> 
> hmmm. I think you want a comma there, not a dot, in the super args.
> And you shouldn't pass self as an argument here, either.  Just:

Sorry about the dot, a little premature copying. That __init__ doesn't
take self is an interesting artifact of the implementation [super(..)
seems to want to be object substitutable, but only is some of the
time...]

[...]
> > metaclasses aren't related by inheritance. Trying to fix 
> > this by, e.g.
> 
> "Related by inheritance" may be a bit too weak.  More specifically:

Yes, but not in this case, which is why I didn't want to say:

[..for all B in C.__bases__, C.__metaclass__ must be subclass of
B.__metaclass__...]

Not that I didn't know them, I just haven't figured out why they must be
so restrictive ? I'm guessing it has to do with attribute lookup rules,
however I haven't been able to find a good description of attribute
lookup for new-style classes... (references?) E.g. why is the metaclass'
__getattr__ never called?

[..]
> > making metaIC a subclass of metaMetaBunch (and changing the 
> > __new__ call appropriately), gives you:
> > 
> > Traceback (most recent call last):
> >   File "M:\python\cpoint.py", line 38, in ?
> >     class CountedPoint(Counted, Point):
> >   File "M:\python\cpoint.py", line 25, in __new__
> >     return metaMetaBunch.__new__(cls, name, bases, dict)
> >   File "M:\python\cpoint.py", line 20, in __new__
> >     return type.__new__(cls, classname, bases, newdict)
> > TypeError: multiple bases have instance lay-out conflict
> > 
> > which means you're stuck (?)
> 
> Well no -- you MIGHT be stuck if you ever needed two different AND
> incompatible __new__ in the same class, but here metaIC may just as
> well use __init__ instead (as it ain't messing with e.g. __slots__:-)
> so everything works if you recode the whole mess as, e.g.:

Which is fine as long as you have access to the code of both the Point
and Counted classes and their metaclasses, understand metaclasses in
general, the ramifications of the particular implementation and how
other things would break if you started changing things, and even then
you're stuck if they both need __new__, unless you can code up a
compromise. Which was basically my only point :-) While the abstract
base class solution does have its problems, so does the metaclass
solution (I wouldn't consider mucking with superclasses' implementation
just because you need to multiply inherit as beeing in the OO spirit
<wink>) -- the metaclass solution is aesthetically more pleasing though
:-)

[..nice self consistent reimplementation..]

> But given the dependencies I don't think this particular mixin
> mesh makes much sense.  I'd rather merge two metaclasses into a
> third one (solving any __new__-related conflicts of course;-)
> rather than arbitrarily deriving one from the other (and it IS
> arbitrary -- now you're forcing ANYTHING that's counted to be
> SOME kind of metabunch...).

Well, _I_ just wanted a countable point, someone else forced me into
hacking "magic code" just because I wanted to use regular inheritance
<grin>.

-- bjorn





More information about the Python-list mailing list