Method binding confusion

Peter Otten __peter__ at web.de
Mon May 3 13:52:02 EDT 2004


Robert Brewer wrote:

> Specifically, one needs to explain why:
> 
>>>> kmy.KlassMath.operator
> <built-in function pow>
>>>> kmy.KlassMath().operator
> <built-in function pow>
> 
> but:
> 
>>>> kmy.KlassMyModule.operator
> <unbound method KlassMyModule.mypow>
>>>> kmy.KlassMyModule().operator
> <bound method KlassMyModule.mypow of <kmy.KlassMyModule object at
> 0x0114DCD0>>
> 
> ...which I haven't got the vocabulary or time for right now. ;(

Following Andrew Bennetts' hint and rereading parts of
http://users.rcn.com/python/download/Descriptor.htm
the following is the most striking example that I could come up with to
demonstrate how the existence/absence of a __get__() method controls a
method's behaviour:

>>> import types
>>> class Method(object):
...     def __get__(self, obj, objtype=None):
...             return types.MethodType(self, obj, objtype)
...     def __call__(*args):
...             print "method%r" % (args,)
...
>>> class A: pass
...
>>> A.method = Method()
>>> a = A()
>>> a.method(1,2,3)
method(<__main__.Method object at 0x40296d0c>, <__main__.A instance at
0x40296c0c>, 1, 2, 3)

Now away with __get__():

>>> del Method.__get__
>>> a.method(1,2,3)
method(<__main__.Method object at 0x40296d0c>, 1, 2, 3)
>>>

Bye the way, I tried this with a simple function first, but failed:

>>> def f(): pass
...
>>> del f.__get__
Traceback (most recent call last):
  File "<stdin>", line 1, in ?
AttributeError: 'function' object attribute '__get__' is read-only
>>>

The machinery behind the observed behaviour is now somewhat clearer - I
think you can predict a function's behaviour as a method by checking
hasattr(func, "__get__"). But still the *reason* (or simply use-case) for
this dichotomy of functions (to me) remains unclear. Why are not all
functions created equal?

Peter




More information about the Python-list mailing list