码迷,mamicode.com
首页 > 编程语言 > 详细

python里面的垃圾回收机制

时间:2020-05-12 21:59:35      阅读:101      评论:0      收藏:0      [点我收藏+]

标签:引用   代码   dealloc   全局变量   循环   结构体   图片   删除   定位   

文章链接:https://www.jianshu.com/p/1e375fb40506

 

Garbage collection(GC)

现在的高级语言如java,c#等,都采用了垃圾收集机制,而不再是c,c++里用户自己管理维护内存的方式。自己管理内存极其自由,可以任意申请内存,但如同一把双刃剑,为大量内存泄露,悬空指针等bug埋下隐患。
对于一个字符串、列表、类甚至数值都是对象,且定位简单易用的语言,自然不会让用户去处理如何分配回收内存的问题。
python里也同java一样采用了垃圾收集机制,不过不一样的是:
python采用的是引用计数机制为主标记-清除分代收集两种机制为辅的策略

 

GC系统所承担的工作远比“垃圾回收”多得多。它们负责三个重要任务:

  • 为新生成的对象分配内存
  • 识别那些垃圾对象
  • 从垃圾对象回收内存

  如果将应用程序比作人的身体:所有你所写的那些优雅的代码,业务逻辑,算法,应该就是大脑。垃圾回收就是应用程序那颗跃动的心。像心脏为身体其他器官提供血液和营养物那样,垃圾回收器为你的应该程序提供内存和对象。如果垃圾回收器停止工作或运行迟缓,像动脉阻塞,你的应用程序效率也会下降,直至最终死掉。

 

1、引用计数机制:

python里每一个东西都是对象,它们的核心就是一个结构体:PyObject

 typedef struct_object {
int ob_refcnt; #引用计数
struct_typeobject *ob_type;
} PyObject;

PyObject是每个对象必有的内容,其中ob_refcnt就是做为引用计数。当一个对象有新的引用时,它的ob_refcnt就会增加,当引用它的对象被删除,它的ob_refcnt就会减少
#define Py_INCREF(op)   ((op)->ob_refcnt++) //增加计数
#define Py_DECREF(op) \ //减少计数
    if (--(op)->ob_refcnt != 0)         ;     else         __Py_Dealloc((PyObject *)(op))
 

gc方式1:引用计数

若此对象无其他对象引用,则立马回收掉

优点:简单、实时(将处理垃圾时间分摊到运行代码时,而不是等到一次回收)

缺点:

1.保存对象引用数会占用一点点内存空间

2.每次执行语句都可能更新引用数,不再使用大的数据结构时,会引起大量对象被回收

3.不能处理循环引用的情况

 

gc方式2:标记-清除(Mark—Sweep)

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

技术图片

 

 

处理过程

1.将所有容器对象放到一个双向链表中(链表为了方便插入删除),这些对象为0代

2.循环遍历链表,如果被本链表内的对象引入,自身的被引用数-1,如果被引用数为0,则触发引用计数回收条件,被回收掉

3.未被回收的对象,升级为1代

『标记清除(Mark—Sweep)』算法是一种基于追踪回收(tracing GC)技术实现的垃圾回收算法。它分为两个阶段:第一阶段是标记阶段,GC会把所有的『活动对象』打上标记,第二阶段是把那些没有标记的对象『非活动对象』进行回收。那么GC又是如何判断哪些是活动对象哪些是非活动对象的呢?

对象之间通过引用(指针)连在一起,构成一个有向图,对象构成这个有向图的节点,而引用关系构成这个有向图的边。从根对象(root object)出发,沿着有向边遍历对象,可达的(reachable)对象标记为活动对象,不可达的对象就是要被清除的非活动对象。根对象就是全局变量、调用栈、寄存器。

 

何时触发

1.被引用为0时,立即回收当前对象

2.达到了垃圾回收的阈值,触发标记-清除

3.手动调用gc.collect()

4.Python虚拟机退出的时候

 




python里面的垃圾回收机制

标签:引用   代码   dealloc   全局变量   循环   结构体   图片   删除   定位   

原文地址:https://www.cnblogs.com/1314520xh/p/12879073.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!