Golang 垃圾回收
2022/4/22 6:16:23
本文主要是介绍Golang 垃圾回收,对大家解决编程问题具有一定的参考价值,需要的程序猿们随着小编来一起学习吧!
Go 垃圾回收使用的是标记-回收算法,分为四个阶段:标记准备阶段,标记阶段,标记终止阶段,清理阶段。
一、垃圾回收流程
1)标记准备阶段
进行的操作:
- 判断当前协程是否可以抢占,不可以抢占不触发GC;
- 启动后台标记协程;
- 暂停用户协程(STW - stop the word);
- 开启写屏障;
- 将根对象入队;
标记协程的启动数量?
每个逻辑处理器P会启动一个标记协程,但并不是每个标记协程都会执行,同时执行的标记协程数量大约是P的25%,也就是有25%的CPU用在GC上。例如,有4个P,那同一时间只有1个标记协程在执行。这样做可以减少GC给用户程序带来的影响。
[代码:runtime/mgc.go.startCycle()]
标记协程的调度过程?
STW后,重新启动所有协程,调度器会进行新的一轮调度,这时会判断程序是否处于GC阶段,如果是则判断是否需要执行标记任务。怎么判断呢?分两种情况:
第一种,需要执行的标记协程数(dedicatedMarkWorkersNeeded)大于0时,此时是DedicatedMode模式;
第二种,fractionalUtilizationGoal大于0且当前P执行标记任务的时间小于fractionalUtilizationGoal*当前标记周期的时间,这种情况只会占用部分时间来进行标记任务,超出时间后,其它协程可以抢占,此时是FractionalMode模式。
[代码:runtime/mgc.go.findRunnableGCWorker()]
为什么要开启写屏障?
因为用户协程和标记协程是并发执行的,在标记的过程中,函数栈内可能会有新分配的对象,如果没有开启写屏障,那新分配的对象是标记为白色的,可能会在这次GC中被误回收。写屏障的作用就是把新分配的对象标记为灰色,避免误回收,这些灰色对象会在下次GC中判断是否需要回收。
根对象包含什么?
根对象包含了全局对象、栈对象(goroutine栈)
2)标记阶段
进行的操作:
- 恢复用户协程;
- 使用三色标记法开始标记,此时用户协程和标记协程并发执行;
标记任务的模式有哪些?
1、DedicatedMode:代表当前P专门负责标记对象,不会被抢占;
2、FractionalMode:在标记任务到达目标时间后,会自动退出;
3、IdleMode:当前P没有可以执行的G,执行标记任务,直到被抢占;
在DedicateMode模式中,协程不能被抢占,那这个P中的G将得不到执行,怎么办呢?
先执行可以被抢占的标记协程,如果标记协程已经被抢占了,则将当前P中的G挪到全局队列中,进入不能被抢占的模式
三色标记法:
黑色对象:对象已被标记,包含的子对象也被标记,不会在本次GC中回收
灰色对象:对象已被标记,但包含的子对象尚未标记,不会在本次GC中回收
白色对象:对象未标记,会在本次GC中回收
三色标记法用是否可达来判断对象是否存活,首先会扫描根对象,将根对象引用的对象标记为灰色;然后处理灰色对象,将灰色对象引用的对象标记为灰色,自身标记为黑色,循环处理灰色对象,直到灰色对象集合为空,此时只剩黑色对象和白色对象
3)标记终止阶段
进行的操作:
- 暂停用户协程
- 计算下一次触发GC时需要达到的堆目标
- 唤醒后台清扫协程
4)清理阶段
进行的操作:
- 关闭写屏障
- 恢复用户协程
- 异步清理回收
二、垃圾回收触发时机
- 内存分配量达到阈值:每次内存分配都会判断当前内存是否达到阈值,如果是则触发GC。阈值为当前堆内存达到2倍上一次GC后的内存,2倍为内存增长率,可通过环节变量GOGC调整;
- 定时触发:默认2分钟触发一次,这个配置在runtime/proc.go里的forcegcperiod参数;
- 手动触发:使用runtime.GC() 手动触发;
浅析 Golang 垃圾回收机制
深入理解Go-垃圾回收机制
《Go 语言底层原理剖析》 - 郑建勋
这篇关于Golang 垃圾回收的文章就介绍到这儿,希望我们推荐的文章对大家有所帮助,也希望大家多多支持为之网!
- 2024-11-15SendGrid 的 Go 客户端库怎么实现同时向多个邮箱发送邮件?-icode9专业技术文章分享
- 2024-11-15SendGrid 的 Go 客户端库怎么设置header 和 标签tag 呢?-icode9专业技术文章分享
- 2024-11-12Cargo deny安装指路
- 2024-11-02MongoDB项目实战:从入门到初级应用
- 2024-11-01随时随地一键转录,Google Cloud 新模型 Chirp 2 让语音识别更上一层楼
- 2024-10-25Google Cloud动手实验详解:如何在Cloud Run上开发无服务器应用
- 2024-10-24AI ?先驱齐聚 BAAI 2024,发布大规模语言、多模态、具身、生物计算以及 FlagOpen 2.0 等 AI 模型创新成果。
- 2024-10-20goland工具下,如修改一个项目的标准库SDK的版本-icode9专业技术文章分享
- 2024-10-17Go学习:初学者的简单教程
- 2024-10-17Go学习:新手入门完全指南