作者:咬__唇 | 来源:互联网 | 2023-05-24 17:15
Python编译器生成的代码对象包含指令(命名co_consts
)中使用的常量元组以及包含名称(命名co_names
)的元组.
为什么有两个不同的列表?仅使用co_consts
名称也不简单吗?
1> Dunes..:
考虑以下功能.
def f(x):
x += n
return x * 4
这x
是一个本地名称,其值可以更改.4
是一个常数.它的价值永远不会改变.但是,它仍然是一个对象,最好缓存它们,而不是每次需要时创建一个新对象.最后,n
是一个全球参考.该字符串"n"
由函数存储,以便它可以用作n
从函数的全局上下文中检索的键.
>>> f.__code__.co_nlocals # just 1 (for x)
1
>>> f.__code__.co_consts
(None, 4)
>>> f.__code__.co_names
('n',)
>>> "n" in f.__globals__ and globals() is f.__globals__
True
保持名称和内容分离的原因是为了内省.合并元组的唯一真正原因是内存效率,尽管这只会获得一个对象和每个函数一个指针.考虑以下功能.
def g():
return "s" * n
如果包含consts的元组与包含名称的元组合并,那么你(不是VM)将无法分辨哪些值用于访问全局变量以及哪些是函数的常量.