为何Python字符串驻留与数字驻留机制表现不同?附代码示例
为什么Python中字符串驻留与数字驻留机制存在差异?
这本质是Python针对不同不可变类型的内存优化策略差异,核心是权衡「驻留收益」和「实现成本」:
1. 小整数的驻留策略:预缓存高频值
Python会在启动时就预加载(缓存)-5到256之间的所有整数对象,这个范围内的整数是程序中最常使用的,预缓存的成本极低,但能大幅减少重复创建对象的开销。
不管是直接赋值(a=5)还是通过运算生成(b=4; b+=1),只要结果落在这个区间,解释器都会直接返回缓存中的现有对象,所以a is b会返回True——两者指向同一个内存地址的整数对象。
2. 字符串的驻留策略:仅针对编译时字面量
字符串的可能取值远多于小整数,若对所有字符串都自动驻留,会带来极高的内存和计算开销(比如哈希存储、碰撞处理等)。因此Python只对编译时就能确定的字符串字面量自动驻留:
- 直接赋值的字符串(
s1='string') - 编译时可合并的字符串拼接(比如
s2='strin'+'g',编译阶段会被优化为s2='string')
而像s2 += 'g'这种运行时动态拼接的字符串,解释器不会自动将其加入驻留池——无法提前预判结果,且动态生成的字符串可能数量庞大、内容多变,驻留的收益远低于成本。所以s1(驻留的字面量对象)和s2(运行时生成的新对象)指向不同的内存地址,s1 is s2返回False。
补充验证:编译时拼接的字符串会被驻留
如果把字符串拼接放在编译阶段,结果就会和整数案例一致:
s1 = 'string' s2 = 'strin' + 'g' # 编译时合并为字面量 print(s1 is s2) # 输出 True
你也可以用sys.intern()手动强制驻留运行时生成的字符串,此时is比较会返回True:
import sys s1 = 'string' s2 = 'strin' s2 += 'g' s2 = sys.intern(s2) print(s1 is s2) # 输出 True
内容的提问来源于stack exchange,提问作者Sahil Lohiya
相关产品推荐
相关产品推荐

