Go 内存管理 | 青训营笔记

64 阅读2分钟

这是我参与「第五届青训营 」伴学笔记创作活动的第 4 天

Go 内存管理

Copying GC: 将存活对象从一块内存空间复制到另外一块内存空间,原先的空间可以直接进行对象分配

5589aa6bb368a6c10a3f5c3774f6723d_f626b4ba791d467fa5eccae94ebe259b.png Mark-compact GC: 将存活对象复制到同一块内存区域的开头

d3126fd35d4bb08850522494146071c3_4227aec6c9e94ef58ccb13ee75b45ad8.png

内存分配--分块

先向os申请一大块内存如4MB,再将4MB分块,如8KB,称作mspan 再将mspan分块用于对象分配

b64f87a625d3ba8ac9b13e85142e4475_208fbebddccf47dbbfa4ba3d626a2052.png

内存分配--缓存

如果内存被回收,不会立刻归还给os,先在goruntime内部缓存起来,避免频繁向os申请内存。 1.mcache中mspan分配完了,就向mcentral申请未分配的mspan 2.mcache中mspan没有分配的对象,mspan会被缓存在mcentral中,不会立刻还给os

f96d8fa1798c4bf940c470a5dcbc93af_3fa26426ab42401180a28756ce898cf9.png 由于对象分配是高频操作,小对象占比高,内存分配比较耗时 分配路径: g->m->p->mcache->mspan->memory block->return pointer

Balanced GC

该优化方案是为了减少小对象的分配 本质:将多个小对象分配合并成一个大对象的分配

每个 g 会附加一个较大的 GAB (例如 1 KB) 用来分配小于 128 B 的 noscan 小对象 然后根据对象大小移动 top 指针并返回,快速完成一次对象分配

但会存在问题,GAB中只有一个小对象存活,goruntime 也会认为整个GAB是存活的 这样的问题就还原回一开始的GC,当GAB1中存活对象低于某个阈值,只需要将GAB1中存活的对象移动到另一个GAB2,就可以释放掉GAB1了。

991f98099d20903c3cd822b4b8f4b174_c273d5fa8a3f4941976297cb4c8c6ba0.png

总结

这一部分内容更加难懂,但比java的jvm应该简单一些,也只是作初步了解,往后再作深入学习。

图片转载自:blog.csdn.net/Gherbirthda…