python - 为什么 python VM 有 co_names 而不是仅仅使用 co_consts?

标签 python bytecode vm-implementation

Python 编译器生成的代码对象包含指令中使用的常量元组(名为 co_consts )以及包含名称的元组(名为 co_names )。

为什么有两个不同的列表?使用 co_consts 不会更简单也是为了名字?

最佳答案

考虑以下函数。

def f(x):
    x += n
    return x * 4

这里的x是一个局部名称,它的值可以改变。 4 是一个常量。它的值(value)永远不会改变。但是,它仍然是一个对象,最好将它们缓存起来,而不是每次需要时都创建一个新对象。最后,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

将名称和常量分开的原因是为了内省(introspection)。合并元组的唯一真正原因是内存效率,尽管这只会为每个函数获得一个对象和一个指针。考虑以下函数。

def g():
    return "s" * n

如果包含常量的元组与包含名称的元组合并,那么您(不是虚拟机)将无法分辨哪些值用于访问全局变量,哪些是函数的常量。

关于python - 为什么 python VM 有 co_names 而不是仅仅使用 co_consts?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/28187661/

相关文章:

python - PyQT5 QSystemTrayIcon 激活信号不起作用

c - 汇编、机器码、字节码和操作码之间的实际关系是什么?

java - 为什么在创建新实例时进行 DUP

java - 在运行时创建 Pojo 并将其保存在磁盘上?

virtual-machine - LLVM中的VM在哪里?

.net - .NET 内存管理在托管代码中是否比在 native 代码中更快?

python - Pandas 发送多个 DataFrames to_csv

python - 如何向 Bokeh 条形图添加标签?

python - 如何使用字符串获取函数?

compiler-construction - 为什么需要虚拟机?