Python 加等于慢



我使用比较两种不同的_accumulator_方式timeit.repeat进行了一些快速基准测试。

def testAccumPlusEqual():
    x = 0
    for i in range(100):
        x += 1
    return x
def testAccumEqualPlus():
    x = 0
    for i in range(100):
        x = x + 1
    return x

我对timeit.repeat的实现是:

if __name__ == '__main__':
    import timeit
    print(timeit.repeat("testAccumPlusEqual()",
                    setup="from __main__ import testAccumPlusEqual"))
    print(timeit.repeat("testAccumEqualPlus()",
                    setup="from __main__ import testAccumEqualPlus"))

结果如下:

>>> 
[8.824021608811469, 8.80440620087051, 8.791231916848997]
[8.101681307351758, 8.143080002052649, 8.181129610882778]

诚然,在宏伟的计划中,这种时差可能并不明显,但如果大规模使用,可能会导致减速。所以我想我真的在问:

从我所见过的任何地方来看,事实上的标准是积累+=,但事实仍然如此吗?

为什么+=的表现会比x=x+差?

注意:在Windows 7 64位上使用CPython 3.3.2(使用32位版本的python)

这实际上不是一个答案,但它可以帮助你理解Python代码中发生了什么。您可以在两个函数上调用 dis 并获取:

>>> import dis
>>> dis.dis(testAccumEqualPlus)
  2           0 LOAD_CONST               1 (0)
              3 STORE_FAST               0 (x)
  3           6 SETUP_LOOP              30 (to 39)
              9 LOAD_GLOBAL              0 (range)
             12 LOAD_CONST               2 (100)
             15 CALL_FUNCTION            1
             18 GET_ITER            
        >>   19 FOR_ITER                16 (to 38)
             22 STORE_FAST               1 (i)
  4          25 LOAD_FAST                0 (x)
             28 LOAD_CONST               3 (1)
             31 BINARY_ADD          
             32 STORE_FAST               0 (x)
             35 JUMP_ABSOLUTE           19
        >>   38 POP_BLOCK           
  5     >>   39 LOAD_FAST                0 (x)
             42 RETURN_VALUE        
>>> dis.dis(testAccumPlusEqual)
  2           0 LOAD_CONST               1 (0)
              3 STORE_FAST               0 (x)
  3           6 SETUP_LOOP              30 (to 39)
              9 LOAD_GLOBAL              0 (range)
             12 LOAD_CONST               2 (100)
             15 CALL_FUNCTION            1
             18 GET_ITER            
        >>   19 FOR_ITER                16 (to 38)
             22 STORE_FAST               1 (i)
  4          25 LOAD_FAST                0 (x)
             28 LOAD_CONST               3 (1)
             31 INPLACE_ADD         
             32 STORE_FAST               0 (x)
             35 JUMP_ABSOLUTE           19
        >>   38 POP_BLOCK           
  5     >>   39 LOAD_FAST                0 (x)
             42 RETURN_VALUE

如您所见,唯一的区别是+= INPLACE_ADD= .. + BINARY_ADD

相关内容

  • 没有找到相关文章

最新更新