[Tutor] Counting method calls
Kent Johnson
kent37 at tds.net
Sat Sep 22 18:46:37 CEST 2007
Ricardo Aráoz wrote:
> Kent Johnson wrote:
>> What version of Python are you using? When I try this program it prints
>
> Py 0.9.5
> Python 2.5 (r25:51908, Sep 19 2006, 09:52:17) [MSC v.1310 32 bit
> (Intel)] on win32
>
> I thought it might be you were trying the class with the list init call
> but I tried it and works the same way.
> Was using PyAlaMode, tried it using IDLE and it works like yours,
> probably a bug of PyAlaMode.
My guess is PyAlaMode is trying to introspect the objects in some way
and that is causing the extra access (to non-existent attributes).
>> class CallCounter(object):
>> def __init__(self, delegate):
>> self._delegate = delegate
>> self.calls = 0
>> def __getattr__(self, name):
>> value = getattr(self._delegate, name)
>> if callable(value):
>> self.calls += 1
>> return value
>>
>> a = CallCounter(list())
>
> Sadly :
>>>> a = CallCounter(list())
>>>> a.append(1)
>>>> a.calls
> 2
>>>> a.append(2)
>>>> a.append(3)
>>>> a.calls
> 5
>>>> a[3]
>
> Traceback (most recent call last):
> File "<pyshell#15>", line 1, in <module>
> a[3]
> TypeError: 'CallCounter' object is unindexable
Hmm. The problem is that new-style classes don't look up special methods
on instances, just in the class itself.
There is some discussion here, it looks a bit ugly:
http://groups.google.com/group/comp.lang.python/browse_thread/thread/c5bb6496970b5c5a?hl=en&tvc=2
Alex Martelli's second response proposes a solution that overrides
__new__() to create a custom class for each wrapper.
There might be some help here too, I haven't read it closely:
http://tinyurl.com/25lx5t
The code works if CallCounter is an old-style class.
Kent
More information about the Tutor
mailing list