【发布时间】:2017-12-28 14:59:09
【问题描述】:
这是一个优化问题。我在函数中有一个表达式,如下所示:
>>> def x():
... num = 2 * 4 * 100 * 20
...
>>> x.__code__.co_consts
(None, 2, 4, 100, 20, 8, 800, 16000)
表达式2 * 4 * 100 * 20的结果是16000,所以如果我们反汇编x:
>>> dis.dis(x)
2 0 LOAD_CONST 7 (16000)
3 STORE_FAST 0 (x)
6 LOAD_CONST 0 (None)
9 RETURN_VALUE
16000 几乎是我们所需要的。 co_consts 商店 8 和 800 从技术上讲不再需要,我们有总数吗?
将上述表达式与另一个表达式进行比较:
>>> def x():
... num = 3 + 4 + 9 * 4
...
>>> x.__code__.co_consts
(None, 3, 4, 9, 7, 36)
看起来字节码编译器接受二进制操作数并存储它们的计算值:
9 * 4 36
3 + 4 7
反汇编函数:
>>> dis.dis(x)
2 0 LOAD_CONST 4 (7)
3 LOAD_CONST 5 (36)
6 BINARY_ADD
7 STORE_FAST 0 (num)
10 LOAD_CONST 0 (None)
13 RETURN_VALUE
有趣的是,如果您采用以下表达式:2 + 5 * 8 - 5 + 23 * 4,co_consts 将是 (None, 2, 5, 8, 23, 4, 40, 92),仅计算乘法:5 * 8 和 23 * 4 忽略了加法和减法。
这种优化如何真正发挥作用?我仅在 2.7 上对此进行了测试。
【问题讨论】:
-
您正在目睹一些窥视孔优化技巧。查看
peephole.c。
标签: python optimization python-internals