为何Python中相同值变量的"is"比较结果不同?
嘿,这个问题其实是Python里的对象复用优化机制在搞事情,我给你唠明白~
先还原一下你大概率碰到的场景(毕竟没贴代码,我根据常见情况推测):
# 第一种情况:两个变量指向同一个对象 var1 = 10 var2 = 10 print(var1 is var2) # 输出 True # 第二种情况:两个变量指向不同对象 var3 = 1000 var4 = 1000 print(var3 is var4) # 输出 False
如果是这个情况,根源就是Python的**小整数池(Integer Pool)**机制。
什么是小整数池?
Python为了省内存、提速度,会提前创建一批常用的小整数对象,存在一个“池子”里。当你创建这个范围内的整数变量时,直接拿池子里的现成对象用,不会重新新建。在你用的Python 3.6.4版本里,这个默认范围是**-5到256**。所以你给var1和var2赋值10(在范围内),它们自然指向同一个对象。
而当你赋值1000(超出这个范围),Python就会每次都新建一个整数对象,所以var3和var4指向的是完全不同的两个对象。
当然,还有另一种可能场景是用了字符串:
# 情况1:复用同一对象 var1 = "test_str" var2 = "test_str" print(var1 is var2) # 输出 True # 情况2:新建不同对象 var3 = "test str with space" var4 = "test str with space" print(var3 is var4) # 可能输出 False
这时候是**字符串驻留(String Interning)**机制在起作用。Python会自动“驻留”一些符合规则的字符串(比如没有特殊字符的短字符串),复用对象;而带空格、特殊字符的复杂字符串,就不一定会被驻留,每次赋值都会新建对象。
重要提醒:==和is的区别
这里得给你划个重点:==是用来判断两个变量的值是否相等,而is是判断两个变量是否指向同一个对象。你能发现差异,用的肯定是is,要是用==的话,两种情况结果都是True,因为比较的是值本身。
验证方法
你可以用id()函数查看变量对应的对象ID,ID相同就说明是同一个对象:
print(id(var1), id(var2)) # 小整数/简单字符串的话,ID完全一样 print(id(var3), id(var4)) # 大整数/复杂字符串的话,ID不一样
总结一下:Python会对那些常用、创建成本低的对象(比如小整数、简单字符串)做复用优化,减少内存开销和创建时间;而超出范围或者复杂的对象,就会每次都新建,这就是你看到两种情况差异的核心原因啦~
内容的提问来源于stack exchange,提问作者bylds

