Golang中的垃圾回收
GC
GC全称为garbage collection,常见的方法有,
- 引用计数(Python使用了这种方式)
- 标记-清除
- 标记-复制
- 标记-整理
三色标记法
Go使用的三色标记法
来做垃圾回收。前面提到的标记算法都有一个问题,运行时会造成STW。三色标记法对“标记”阶段的改进,在不暂停程序的情况下即可完成对象的可达性分析。GC将对象分为3类:
- 白色:未搜索的对象
- 灰色:正在搜索的对象
- 黑色:已经搜索的对象
三色标记法属于增量式GC,回收器首先将所有对象都标记为白色,然后从GC root开始,逐步把所有可达对象变成灰色,再到黑色。最终剩余的白色对象即为不可达对象。
具体实现如下:
- 初始状态下所有对象都为白色
- 从root对象开始,扫描所有可达对象标记为灰色,放入待处理队列
- 从队列中取出一个灰色对象,标记为黑色,将其引用标记为灰色,放入待处理队列
- 重复步骤,直到队列空
读写屏障技术
三色标记法中gc和用户程序同时运行,其实是存在并发性问题的,为了解决这个问题,go使用了读写屏障技术。
编译器会在编译期间生成一段代码,该代码在运行期间会拦截用户的读取,创建,更新对象指针的操作,相当于一个hook调用,根据hook时机不同,分为不同的屏障技术。由于读屏障Read barrier技术需要在读操作中插入代码片段从而影响用户程序性能,所以一般使用写屏障技术来保证三色标记的稳健性。
Golang中的垃圾回收