简而言之:
Python在内部创建一个
C元组对象列表,其第一个元素包含空元组。每次使用
tuple()或时
(),Python都会返回上述
C列表中包含的现有对象,而不创建新对象。
相反,这种机制并不存在,
dict或者 每次都从头开始重新创建的
list对象都不存在。 __
这很可能与以下事实有关:不变的对象(例如元组)无法更改,因此保证在执行期间不会更改。考虑到
frozenset() isfrozenset()回报
True,这一点得到进一步巩固;像
()空一样
frozenset
被认为是实现的单例
CPython。对于可变对象,
此类保证没有到位 ,因此也没有动机来缓存其零元素实例(即,其内容可能会在身份保持不变的情况下发生变化)。
请注意: 这不是一个应该依靠的东西,即,一个人不应该将空元组视为单例。 在文档中没有明确保证此类保证,因此应假定它与实现有关。
怎么做的:
在最常见的情况下,的实现
CPython是用两个宏编译的,
PyTuple_MAXFREELIST并
PyTuple_MAXSAVESIZE设置为正整数。这些宏的正值会导致创建具有size的
tuple对象数组
PyTuple_MAXSAVESIZE。
当
PyTuple_New使用参数调用时,请
size ==0确保将新的空元组添加到列表(如果尚不存在):
if (size == 0) { free_list[0] = op; ++numfree[0]; Py_INCREF(op); }然后,如果请求一个新的空元组,则将返回位于该列表的第一位置的一个元组,而不是一个新的实例:
if (size == 0 && free_list[0]) { op = free_list[0]; Py_INCREF(op); 促使这样做的另一个原因是函数调用构造了一个元组来保存将要使用的位置参数的事实。可以在以下
load_args函数中看到
ceval.c:
static PyObject *load_args(PyObject ***pp_stack, int na){ PyObject *args = PyTuple_New(na); do_call在同一文件中通过调用。如果参数个数
na为零,则将返回一个空的元组。
本质上,这可能是一个经常执行的操作,因此不要每次都构造一个空的元组是有意义的。


![为什么当[[]是[]“而'{}是{}'返回False时,'()是()'返回True? 为什么当[[]是[]“而'{}是{}'返回False时,'()是()'返回True?](http://www.mshxw.com/aiimages/31/639446.png)
