内存管理
内存管理一般包含三个不同的组件,分别是用户程序(Mutator)、分配器(Allocator)和收集器(Collector)1,当用户程序申请内存时,它会通过内存分配器申请新的内存,而分配器会负责从堆中初始化相应的内存区域。 一、内存分配器线性分配(Bump Allocator)是一种高效的内存分配方法,但是有较大的局限性。空闲链表分配器(Free-List Allocator)可以重用已经被释放的内存,它在内部会维护一个类似链表的数据结构。 当用户程序申请内存时,空闲链表分配器会依次遍历空闲的内存块,找到足够大的内存,然后申请新的资源并修改链表。空闲链表分配器可以选择不同的策略在链表中的内存块中进行选择,最常见的就是以下四种方式:
* 首次适应(First-Fit)— 从链表头开始遍历,选择第一个大小大于申请内存的内存块;
* 循环首次适应(Next-Fit)— 从上次遍历的结束位置开始遍历,选择第一个大小大于申请内存的内存块;
* 最优适应(Best-Fit)— 从链表头遍历整个链表,选择最合适的内存块;
* 隔离适应(Segregated-Fit)— 将内存分割成多个链表,每个链表中的内存块大小相同,申请内存时先找到满足条件的链表,再从链表中选择合适的内存块;
内存管理组件
Go 语言的内存分配器包含内存管理单元、线程缓存、中心缓存和页堆几个重要组件。小结:Go 语言为了实现高性能的并发垃圾收集器,使用三色抽象、并发增量回收、混合写屏障、调步算法以及用户程序协助等机制将垃圾收集的暂停时间优化至毫秒级以下。三种不同的触发时机1.后台触发2.手动触发3.申请内存
栈空间管理
栈寄存器在是 CPU 寄存器中的一种,它的主要作用是跟踪函数的调用栈2,Go 语言的汇编代码中包含 BP 和 SP 两个栈寄存器,它们分别存储了栈的基址指针和栈顶的地址
逃逸分析
Go 语言的逃逸分析遵循以下两个不变性:
1.
指向栈对象的指针不能存在于堆中;
2.
指向栈对象的指针不能在栈对象回收后存活;