python进阶--内存管理

小整数池

[-5,256]之间的整数由于经常用到,所以在python启动的那一刻,就会开辟一块内存空间放入这些整数,且不会被垃圾回收机制回收

# 交互模式
>>> aa = 300
>>> bb = 300
>>> id(aa)
140480563327568
>>> id(bb)
140480564159120
>>> aa is bb
False

>>> a = 10
>>> b = 10
>>> id(a)
4418444224
>>> id(b)
4418444224
>>> a is b
True

intern机制和大整数池

  • Python解释器为了提高字符串使用的效率和使用性能,使用了 intern(字符串驻留)的技术来提高字符串效率,即值同样的字符串对象仅仅会保存一份,放在一个字符串储蓄池中,是共用的,当然,肯定不能改变,这也决定了字符串必须是不可变对象
  • 大整数池:存储包含数字、字母、下划线的字符串,且长度不超过20位。
# 交互模式
>>> a = 'helloworld123'
>>> b = 'helloworld123'
>>> a is b
True
>>> aa = 'hello world123'
>>> bb = 'hello world123'
>>> aa is bb
False
>>> aa = 'hello_world123'
>>> bb = 'hello_world123'
>>> aa is bb
True

深拷贝和浅拷贝

通常只在列表嵌套列表时讨论深拷贝和浅拷贝
浅拷贝(copy):拷贝父对象,不会拷贝对象的内部的子对象。所以原始数据子对象改变,子对象会改变
深拷贝(deepcopy): copy 模块的 deepcopy 方法,完全拷贝了父对象及其子对象,所以原始对象的改变不会造成深拷贝里任何子元素的改变

import copy

l0 = [1, 2, 3]   # 内层列表
l = [11, 22, l0]

l1 = l.copy()              # 浅拷贝
l2 = copy.deepcopy(l)      # 深拷贝
print(l1)
print(l2)

l0.append(4)
print(l1)
print(l2)

>
[11, 22, [1, 2, 3]]
[11, 22, [1, 2, 3]]
[11, 22, [1, 2, 3, 4]]  # 浅拷贝里的元素是对原对象元素的引用,因此原对象改变时新对象也变化
[11, 22, [1, 2, 3]]     # 深拷贝里的元素是对原对象元素的复制,因此原对象改变时新对象不会变化

垃圾回收机制

python的垃圾回收机制:引用计数为主,标记清除和分代回收为辅

  • 引用计数

每个对象创建之后都有一个引用计数,当引用计数为0时垃圾回收机制会自动销毁,回收内存空间。

import sys

a = [1,2,3]        # 1
b = a              # 2
c = b              # 3
print(sys.getrefcount(a)) # 4
>4  # 由于参数会自动产生一个临时引用,所以会比预期的引用次数多1
  • 标记清除

此方式主要用来处理循环引用的情况,只有容器对象(list、dict、tuple,instance)才会出现循环引用的情况

  • 分代回收

python gc给对象定义了三种世代(0,1,2),每一个新生对象在0代中,如果它在一轮gc扫描中活了下来,那么它将被移至1代,在那里他将较少的被扫描,如果它又活过了一轮gc,它又将被移至2代,在那里它被扫描的次数将会更少。当某代中被分配的对象与被释放的对象之差达到某一阈值的时候,就会触发gc对该代的扫描。
在循环引用对象的回收中,整个应用程序会被暂停,为了减少应用程序暂停的时间,Python 通过“分代回收”(Generational Collection)以空间换时间的方法提高垃圾回收效率。

import gc

r = gc.get_threshold()
print(r)

>  
(700, 10, 10)  # gc默认值,意思是第0代数量达到最大值700个时,进行gc回收扫描,在第1、2代达到10个时,分别进行gc回收
  • gc模块

python内建的垃圾回收模块,可以调用一些操作来保证垃圾回收和内存不泄漏

# 加载gc模块
import gc

# 垃圾回收
# gc.collect() 返回处理这些循环引用一共释放掉的对象个数
gc.collect()

  • 参考文档

https://www.cnblogs.com/mazinga/p/12685115.html
https://zhuanlan.zhihu.com/p/83251959
https://blog.csdn.net/xiongchengluo1129/article/details/80462651
https://blog.csdn.net/WangYouJin321/article/details/86503322

评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值