Python function calls are expensive. Python object oriented method calls are even more expensive. How can we estimate method call overhead?
By measuring performance of functional redefinition vs performance of class method calls.
One can find out that the overhead of using the OO method calls over functional calls seems to be about 10%; see the test code below. Also, while the cost of functional redefinition is practically zero, one more OO subclass level adds further ~1%, so that the cost of OO one-subclass inheritance redefinition over functional redefinition is about 11%.
Hence, if one chooses OO, it is interesting to keep the class hierarchy tree as simple as possible, and the cost of OO will be about 10%. In practice, this is often acceptable.
(Note that this does not say much about the slowness of Python OO method call performance for simple class precedence trees, but rather about the slowness of the classical Python function call.)
Here is redef_test.py testing code:
#!/usr/bin/env python """ Simple testing of performance cost of functional redefinition vs OO. Results on PCDH23 run on 20041118 are: $ ./redef_test testing performance cost of functional redefinition vs OO ... fun 5.21 fun_redef 5.1 fun_oo 5.68 $ ./redef_test testing performance cost of functional redefinition vs OO ... fun 5.21 fun_redef 5.11 fun_oo 5.66 $ ./redef_test testing performance cost of functional redefinition vs OO ... fun 5.19 fun_redef 5.1 fun_oo 5.67 This means that the function call cost in case of functional redefinition is zero, and in case of OO for a simple one-level class hierarchy is 11%. Of course it will be more in case of deeper/complex class precedence lists, but I haven't measured how much. P.S. On 20041122 were added fun_oo_subclass to confirm that fun_oo and fun_oo_subclass give the same results, as it's mostly due to the OO overhead. One subclass does not add anything big to the overhead; I measured it to be ~1% difference. """ import time from redef_test_slave import fun, fun_redef, fun_oo, fun_oo_subclass def timing(f, a, n=1000000): """Return timing of function F on argument A run N times. Taken from <http://www.python.org/doc/essays/list2str.html>. """ print f.__name__, r = range(n) t1 = time.clock() for i in r: f(a); f(a); f(a); f(a); f(a); f(a); f(a); f(a); f(a); f(a) t2 = time.clock() print round(t2-t1, 3) return def main(): """Simple testing of performance cost of functional redefinition vs OO. """ print "testing performance cost of functional redefinition vs OO ..." timing(fun, 3) timing(fun_redef, 3) timing(fun_oo().fun_oo, 3) timing(fun_oo_subclass().fun_oo_subclass, 3) return if __name__ == '__main__': main()
Here is redef_test_slave.py:
#!/usr/bin/env python def fun(x): return def fun_redef(x): import sys sys.exit(1) def fun_redef(x): return class fun_oo: def fun_oo(self, x): return def fun_oo_subclass(self, x): import sys sys.exit(1) class fun_oo_subclass(fun_oo): def fun_oo_subclass(self, x): return