为什么“if x is None: pass”比单独的“x is None”更快?

问题描述 投票:0回答:1

Python 3.12 中的计时结果(与不同机器上的 3.11 和 3.13 类似):

When x = None:
13.8 ns  x is None
10.1 ns  if x is None: pass

When x = True:
13.9 ns  x is None
11.1 ns  if x is None: pass

Python: 3.12.0 (main, Oct  7 2023, 10:42:35) [GCC 13.2.1 20230801]

怎样才能做到更多花费更少时间?

为什么

if x is None: pass
更快,因为它必须执行相同的
x is None
检查,然后另外检查结果的真值(并且执行或跳过
pass
)?

基准脚本(在线尝试!):

from timeit import repeat
import sys

for x in None, True:
    print(f'When {x = }:')
    for code in ['x is None', 'if x is None: pass'] * 2:
        t = min(repeat(code, f'{x=}', repeat=100))
        print(f'{t*1e3:4.1f} ns ', code)
    print()

print('Python:', sys.version)
python performance cpython micro-optimization python-internals
1个回答
1
投票

看反汇编代码:

>>> import dis
>>> dis.dis('if x is None: pass')
  0           0 RESUME                   0

  1           2 LOAD_NAME                0 (x)
              4 POP_JUMP_IF_NOT_NONE     1 (to 8)
              6 RETURN_CONST             0 (None)
        >>    8 RETURN_CONST             0 (None)
>>> dis.dis('x is None')
  0           0 RESUME                   0

  1           2 LOAD_NAME                0 (x)
              4 LOAD_CONST               0 (None)
              6 IS_OP                    0
              8 RETURN_VALUE

if
外壳具有特殊的
POP_JUMP_IF_NOT_NONE
操作,比
IS_OP
RETURN_VALUE
更快。您可以在这里阅读有关它的详细讨论:https://github.com/faster-cpython/ideas/discussions/154

© www.soinside.com 2019 - 2024. All rights reserved.