这是我参与「第五届青训营 」伴学笔记创作活动的第 10 天
性能优化
字符串 性能
strings.Builder>bytes.Buffer略>>string
string在go是不可变长的类型,每次拼接都要从新分配内存,strings.Builder和bytes.Buffer底层都是[]byte,都有扩容机制。bytes.Buffer在转成string返回时操作的是[]byte整体切片复制转换成string,而strings.Builder是直接转换[]byte的指针为string指针返回
strings.Builder和bytes.Buffer都尽量提前扩容 可以使用空结构体作为占位符不占用空间(底层把大小为0的对象都指向一个公共的位置),即使bool类型也有1字节,例如把map当作set使用
性能优化靠数据不是猜测
优化最大瓶颈而不是细枝末节
不要过早和过度优化
pprof性能优化工具
(程序内设置好pprof)
程序启动后输入http:// http://localhost:6060/debug/pprof/查看pprof信息
在终端go tool pprof "http://localhost:6060/debug/pprof/profile?seconds=10s"查看10秒内的cpu统计信息
topN:查看代码的资源消耗情况
f
lat=0表示函数本身没什么逻辑,只是调用
list XXX:查找xxx有关的资源消耗
web:可视化显示消耗
go tool pprof -http=:8080 "http://localhost:6060/debug/pprof/heap" 查看堆内存(或者在/pprof/首页上点着看也行)
go tool pprof -http=:8080 "http://localhost:6060/debug/pprof/goroutine" 查看协程
,,,/mutex 查看锁
注意用命令行查看时会有一些过滤
pprof原理
cpu:手动开始和结束,每过10ms操作系统发送SIGPROF信号,进程收到信号记录当前调用堆栈,存入写缓冲,每100ms写到输出流
内存:从程序开始到采样时,通过内存采样器记录堆内存使用情况,其他的采集不到,每512KB记录一次(可修改)
alloc_objects:累计申请的对象数,alloc_space:累计申请的内存大小,inuse_objects:当前持有的对象数,inuse_space:当前占用的内存大小
alloc-free=inuse
block阻塞:采样阻塞操作次数和耗时,但是超过一定耗时阈值才记录(可以设置每次都记录)
锁:采样锁争抢次数和耗时,只记录固定比例的锁竞争操作,可设置成每次都记录