2

I'm really confused with functions call speed in Python. First and second cases, nothing unexpected:

%timeit reduce(lambda res, x: res+x, range(1000))

10000 loops, best of 3: 150 µs per loop

def my_add(res, x):
return res + x
%timeit reduce(my_add, range(1000))

10000 loops, best of 3: 148 µs per loop

But third case looks strange for me:

from operator import add
%timeit reduce(add, range(1000))

10000 loops, best of 3: 80.1 µs per loop

At the same time:

%timeit add(10, 100)
%timeit 10 + 100

10000000 loops, best of 3: 94.3 ns per loop
100000000 loops, best of 3: 14.7 ns per loop

So, why the third case gives speed up about 50%?

3 Answers3

8

add is implemented in C.

>>> from operator import add
>>> add
<built-in function add>
>>> def my_add(res, x):
...     return res + x
... 
>>> my_add
<function my_add at 0x18358c0>

The reason that a straight + is faster is that add still has to call the Python VM's BINARY_ADD instruction as well as perform some other work due to it being a function, while + is only a BINARY_ADD instruction.

Fred Foo
  • 355,277
  • 75
  • 744
  • 836
1

The operator module exports a set of efficient functions corresponding to the intrinsic operators of Python. For example, operator.add(x, y) is equivalent to the expression x+y. The function names are those used for special class methods; variants without leading and trailing __ are also provided for convenience.

From Python docs (emphasis mine)

J0HN
  • 26,063
  • 5
  • 54
  • 85
0

The operator module is an efficient (native I'd assume) implementation. IMHO, calling a native implementation should be quicker than calling a python function.

You could try calling the interpreter with -O or -OO to compile the python core and check the timing again.

Laur Ivan
  • 4,117
  • 3
  • 38
  • 62
  • 1
    All Python code gets compiled to bytecode, `-O` just strips debugging instructions like `assert` and `if __debug__` blocks. – kindall Nov 18 '13 at 16:02
  • You're right. I was under the false impression that -O would do the same as gcc. This happens in [pypy](http://doc.pypy.org/en/latest/config/opt.html). Also, [this](http://stackoverflow.com/questions/4777113/what-does-python-optimization-o-or-pythonoptimize-do). – Laur Ivan Nov 18 '13 at 16:30