哪些类型的Python对象是用引用初始化的,哪些不是?

哪些类型的Python对象是用引用初始化的,哪些不是?,python,reference,garbage-collection,cpython,Python,Reference,Garbage Collection,Cpython,我在Windows上玩Python 3.7中的sys.getrefcount。我尝试了以下方法: 导入系统 >>>x=“这是一个任意字符串” >>>sys.getrefcount(x) 2. 我知道其中一个引用是x,另一个是sys.getrefcount内部使用的参数。无论x初始化为哪种类型,这似乎都有效。然而,我注意到一些奇怪的行为,当我在通过考试之前没有分配任务时: 导入系统 >>>sys.getrefcount(“任意字符串”) 2. >>>sys.getrefcount(1122334

我在Windows上玩Python 3.7中的
sys.getrefcount
。我尝试了以下方法:

导入系统 >>>x=“这是一个任意字符串” >>>sys.getrefcount(x) 2. 我知道其中一个引用是
x
,另一个是
sys.getrefcount
内部使用的参数。无论
x
初始化为哪种类型,这似乎都有效。然而,我注意到一些奇怪的行为,当我在通过考试之前没有分配任务时:

导入系统 >>>sys.getrefcount(“任意字符串”) 2. >>>sys.getrefcount(1122334455) 2. >>>系统getrefcount(1122334455+1) 2. >>>sys.getrefcount(frozenset()) 2. >>>sys.getrefcount(set()) 1. >>>sys.getrefcount(对象()) 1. >>>sys.getrefcount([]) 1. >>>sys.getrefcount(λx:x) 1. >>>sys.getrefcount(范围(1122334455)) 1. >>>sys.getrefcount(dict()) 1. >>>sys.getrefcount(()) 8341 >>>sys.getrefcount(tuple()) 8340 >>>sys.getrefcount(列表(“任意字符串”)) 1. >>>sys.getrefcount(元组(“任意字符串”)) 1. >>>sys.getrefcount((“a”、“r”、“b”、“i”、“t”、“r”、“a”、“r”、“y”、“s”、“t”、“r”、“i”、“n”、“g”)) 2. 这是怎么回事?看起来不可变类型有两个引用,而可变类型只有一个?为什么有些对象似乎是在传递之前分配的,而另一些对象只有一个引用作为参数? 这与
str
/
int
/
tuple
interment有关吗


编辑:一个更直接的问题:为什么选择像
frozenset()
这样的不可变类型在构造时有一个引用,而像
set()
这样的可变类型没有?我单独理解为什么您可能会选择保留此全局范围引用,或者不全面保留,但为什么会存在差异?

一个有趣的问题,因此这里有一个有趣的问题

您应该尝试
getrefcount(2)
,对我来说,它返回93,这意味着CPython为相同的内存地址保留93个引用,保留数字2,因此它不必再次分配它,因为它是不可变的,所以完全可以这样做

现在,让我们尝试两种不同的方法:

#首先
getrefcount(set())#返回1
#第二
s=集合()
getrefcount(s)#返回2
因为它是可变类型,所以当您创建可变类型(
set()
)时,它的行为是不同的,它将在内存中分配它,并且只有一个对它的引用,该引用将在此行结束后立即删除。但是在第二个步骤中,我们定义变量并分配它,当计算引用时,我们有
s
使用的变量和函数
getrefcount
中使用的变量


在Python中,这就是它返回大量数字的原因,CPython保留了大量对空元组的引用。

我想我的问题有一个更具体的形式:为什么选择像
frozenset()
这样的不可变类型在构造时有引用,而像
set()
这样的可变类型没有?我单独理解为什么您可能会选择保留此全局范围引用,或者不全面保留,但为什么会存在差异?