Why is if True slower than if 1? Why is if True slower than if 1? python python

Why is if True slower than if 1?


True and False are not keywords in Python 2.

They must resolve at runtime. This has been changed in Python 3

Same test on Python 3:

>>> timeit.timeit('test1()',setup="from __main__ import test1", number=10000000)2.806439919999889>>> timeit.timeit('test2()',setup="from __main__ import test2", number=10000000)2.801301520000038>>> timeit.timeit('test3()',setup="from __main__ import test3", number=10000000)2.7952816800000164>>> timeit.timeit('test4()',setup="from __main__ import test4", number=10000000)2.7862537199999906

Time error is in 1%, which is acceptable.


Bytecode disassembly makes difference obvious.

>>> dis.dis(test1)  2           0 LOAD_GLOBAL              0 (True)              3 JUMP_IF_FALSE            5 (to 11)              6 POP_TOP               3           7 LOAD_CONST               1 (1)             10 RETURN_VALUE                >>   11 POP_TOP               5          12 LOAD_CONST               2 (0)             15 RETURN_VALUE                     16 LOAD_CONST               0 (None)             19 RETURN_VALUE        

As Kabie mentioned, True and False are globals in Python 2. Lots of stuff is going on to access them.

>>> dis.dis(test2)  3           0 LOAD_CONST               1 (1)              3 RETURN_VALUE        

Python compiler was able to recognize 1 as a constantly "truthy" expression and optimize redundant condition away!

>>> dis.dis(test3)  2           0 LOAD_GLOBAL              0 (True)              3 JUMP_IF_FALSE            5 (to 11)              6 POP_TOP               3           7 LOAD_GLOBAL              0 (True)             10 RETURN_VALUE                >>   11 POP_TOP               5          12 LOAD_GLOBAL              1 (False)             15 RETURN_VALUE                     16 LOAD_CONST               0 (None)             19 RETURN_VALUE        

Pretty much the same as test1, with one more LOAD_GLOBAL.

>>> dis.dis(test4)  3           0 LOAD_GLOBAL              0 (True)              3 RETURN_VALUE        

See test2. But LOAD_GLOBAL is a bit more costly than LOAD_CONST.