Adam Donahue wrote: >>>> class X( object ): > ... def c( self ): pass > ... >>>> X.c > <unbound method X.c> >>>> x = X() >>>> x.c > <bound method X.c of <__main__.X object at 0x81b2b4c>> > > If my interpretation is correct, the X.c's __getattribute__ call knows > the attribute reference is via a class, and thus returns an unbound > method (though it does convert the value to a method).
No, that's wrong. It's not the __getattribute__ of "X.c", it's the __getattribute__ of "X" itself:: >>> type.__getattribute__(X, 'c') <unbound method X.c> >>> X.c.__getattribute__('c') Traceback (most recent call last): File "<interactive input>", line 1, in <module> AttributeError: 'function' object has no attribute 'c' In the former case, we use the type's __getattribute__, and we get the unbound method as expected. In the latter case, we ask the unbound method object for an attribute which it doesn't have Basically, classes define a __getattribute__ that looks something like:: def __getattribute__(self, name): value = object.__getattribute__(self, name) if hasattr(value , '__get__'): return value .__get__(None, self) return value For more information, read: http://users.rcn.com/python/download/Descriptor.htm STeVe -- http://mail.python.org/mailman/listinfo/python-list