Go语言优化 | 青训营笔记

68 阅读3分钟

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

一、本堂课重点内容:

  • Go语言性能

二、详细知识点介绍:

  • 性能优化层面
  1. 业务代码-SDK-基础库-语言运行时-OS

  2. 在业务层优化时,针对特定场景,具体为你具体分析;在语言运行时优化,可以解决更通用的性能问题;数据驱动来进行优化,首先优化最大瓶颈

  3. 在保证接口质量稳定的前提下进行改进,测试用例尽可能地覆盖多地场景,文档写清楚做了什么,没做什么,要添加隔离选项,一键可降级优化,也要有必要地日志输出

  • 自动内存管理
  1. 管理的是动态内存,也就是程序在运行时根据需求动态分配的内存:malloc()。Go语言有自动内存管理,也就是垃圾回收,由程序语言的运行时系统管理动态内存,保证内存使用的正确性和安全性;gc的三个主要任务,为新对象分配空间,找到存活对象,回收死亡对象的内存空间。
Mutator //业务线程,分配新对象,修改对象指向关系
Collertor //GC线程,找到存活对象,回收死亡对象的内存空间
Serial GC //只有一个Collector
Paraller GC //支持多个collectors同时回收的GC算法
Concurrent GC //mutator(s)和 collector(s)可以同时执行
  1. 评价GC,安全性:不能回收存活的对象;吞吐率:1-GC/程序执行总时间;暂停总时间:业务是否感知;内存开销:GC元数据开销
  2. GC追踪垃圾回收,标记根对象(静态变量、全局变量、常量、线程栈),找到可达对象(求指针指向关系的传递闭包;清理不可达对象(将存活对象复制到另外的内存空间;将死亡对象的内存标记为可分配;移动并整理存活对象。
  3. 分代GC,对不同年龄的对象,制定不同的GC策略,降低整体内存管理的开销。不同年龄的对象处于heap的不同区域。年轻代,常规的对象分配;由于存活对象很少,可以采用copying collection。老年代对象一直或者,反复复制开销较大,使用mark-sweep collection。
  4. 引用计数,每个对象都有一个与之关联的引用数目,对象存活的条件:当且仅当引用数大于0。C++智能指针等。优点有内存操作被平摊到程序执行过程中;缺点维护引用计数的开销较大,通过原子操作保证对引用计数操作的原子性和可见性,无法回收环形数据结构;内存开销;引发暂停
  • Go内存管理及优化
  1. 内存分配:调用系统调用mmap申请内存,分成大块,再把大块分成小块。对象分配非常频繁。分配路径长g-m-p-mcache-mspan-memory block-return pointer。pprof是调用最多的。
  2. Balanced GC,每个g绑定一大块内存(1kb),进行小内存分配