Python 变量名称如何在内部存储和映射?
我读过,似乎在CPython中,变量只是与引用关联的名称 对于x=5的语句,有几种情况:Python 变量名称如何在内部存储和映射?,python,variables,cpython,python-internals,Python,Variables,Cpython,Python Internals,我读过,似乎在CPython中,变量只是与引用关联的名称 对于x=5的语句,有几种情况: 将创建一个值为5的int对象(如果已创建,则会找到该对象) 存在) 将创建名称x(或与最后一个对象解除关联) “x”标记) 新(或找到的)int对象的引用计数为 增加1 名称x与具有 已创建(或找到)值“5” 然而,我仍然不清楚变量是如何在内部实现的 即: 创建名称x(或与标记的最后一个对象“x”解除关联) 那么这个名字不也会占用内存空间吗sys.sizeof(x)等于sys.sizeof(5),我得到sy
sys.sizeof(x)
等于sys.sizeof(5)
,我得到sys.sizeof(x)
只能返回关联引用的大小,但是名称x
的大小是多少
dict
,其中键是变量名(str
?),值是与之关联的引用
我认为在较高的层次上,它可以通过dict来完成,其中键是变量名(str?),值是与之关联的引用
这也是它内部工作的方式。在CPython中,变量名及其指向的对象通常存储在Python字典中;编写Python代码时可以使用的数据结构
写入x=5
时,名称x
被设置为全局名称字典中的一个键,对应的值为5。您可以使用globals()
函数返回并检查此字典,该函数提供当前作用域命名空间的内容
因此,名称x
占用空间也是正确的。它作为字符串存在于内存中的某个位置,Python为字典的键保留对它的引用
如果您想更深入地查看CPython源代码,查看将x
分配给值5的位置,可以查看ceval.c。写入x=5
会触发LOAD_CONST
操作码(将整数5放入堆栈)和STORE_GLOBAL
opcode*(将名称x
设置为字典中的键,并将5作为值)
是STORE\u GLOBAL
操作码的代码:
目标(存储\全局){
PyObject*name=GETITEM(名称,oparg);
PyObject*v=POP();
INTERR;
err=PyDict_SetItem(f->f_globals,name,v);
Py_DECREF(v);
如果(错误!=0)
转到错误;
分派();
}
您可以看到调用PyDict_SetItem
来更新globals字典
*如果您检查
x=5
(例如使用dis
)生成的字节码,您可能会看到使用的操作码。此操作码以相同的方式工作(请参阅以获取简要说明)。“这是如何在内部实现的?”-在CPython中?你应该阅读,例如,为了获得更高层次的理解,如果你真的想理解其中的精髓,那么就应该深入研究适当的源代码。(例如,对于CPython,)发现让它更清晰。