getattr(foo, 'foobar') not the same as foo.foobar?
bruno.42.desthuilliers at wtf.websiteburo.oops.com
Fri Mar 14 14:06:30 CET 2008
Dave Kuhlman a écrit :
> Arnaud Delobelle wrote:
>> 4. Both points above follow from the fact that foo.bar is really a
>> function call that returns a (potentially) new object: in fact what
>> really happens is something like
> Arnaud and Imri, too -
> No. foo.bar is *not* really a function/method call.
>> Foo.__dict__['bar'].__get__(foo, Foo).
>> So every time foo.bar is executed an object is (or may be) created,
>> with a new id.
> I appreciate the help, but ...
> Actually, it does not help, because ...
> My understanding is that foo.bar does *not* create a new object.
Given your implementation, foo.bar *does* create a new object on each
lookup. This object is an instancemethod instance, that is, a thin
wrapper around Foo, foo and Foo.__dict__['bar']. Foo.__dict__['bar'] is
a function instance, it's an attribute of class Foo, and the function
class implements the descriptor protocol. So when bar is looked on a Foo
instance, bar.__get__ is called with foo and Foo as arguments, and
returns an instancemethod instance that has .im_self bound to foo,
.im_class bound to Foo, and .im_func bound to Foo.__dict__['bar'].
> All it
> does is return the value of the bar attribute of object foo.
Yes. But since function bar is a descriptor, foo.bar is a computed
attribute, which value is a newly created instancemethod object.
> What new
> object is being created?
> If I have:
> class Foo(object):
> def bar(self): pass
> And I do:
> foo = SomeClass()
> should return the same (identical) object everytime, no? yes?
> I'm still confused.
Then you have to learn how attribute lookup works in Python.
More information about the Python-list