Id是不可变类型

时间:2010-11-27 19:16:04

标签: python

我对可变对象和不可变对象之间的区别感到有些困惑。我尝试了以下代码块来查找对象的id:

tuple1 = ('Object1', 'Object2')
print id(tuple1)
tuple2 = ('Object1', 'Object2')
print id(tuple2)
list1 = ['Object1', 'Object2']
print id(list1)
list2 = ['Object1', 'Object2']
print id(list2)
string1 = "Foo bar"
print id(string1)
string2 = "Foo bar"
print id(string2)

我为字符串获取了相同的id,并为列表提供了不同的id,但是元组的id不同。他们不应该拥有相同的身份证吗?我想知道是否有人可以解释它是如何工作的?

由于

4 个答案:

答案 0 :(得分:4)

相同的ID意味着完全相同的对象,但Python的实现可以随意优化不可变对象的创建。例如,在CPython 2.6.6中,缓存了小整数对象,因此:

>>> x=256
>>> x is 256
True
>>> x=1024
>>> x is 1024
False

[NOTE: 'is' tests for object identity (same ID)]

无法保证此结果在其他实现中是相同的。实现可以缓存不可变元组,但哪些元组是常见的?如果你建议所有相同的元组返回相同的id,那么程序创建的所有元组都必须被缓存,并且元组的每个新创建都必须搜索缓存以查看它是否之前已创建,这将是耗时。

使用==测试对象是否相等,无论ID如何。

答案 1 :(得分:3)

您获得与字符串相同的id,因为字符串文字可以是interned。你没有为元组获得相同的id,因为元组没有被实现。

一个可变的数据结构无法合理地被实现(读取:这样做会导致非常混乱的行为),因此如果字符串是可变的,则它们无法被实现。但是,这并不意味着所有不可变数据结构都被实现。

答案 2 :(得分:1)

Immatable意味着您无法更改类的实例。例如:

salad = ["Lettuce","Tomato","Onion","Tuna"]
fruit = ("Apple","Banana","Cherry","Fig","Grapefruit")
salad[3] = "Cheese"   # works
fruit[3] = "Orange"   # error message

答案 3 :(得分:1)

默认情况下,解释器只为小整数或字符串创建一个共享对象。

相关问题