服务出现fatal error: runtime: out of memory报错,导致服务挂掉,下面分享一个已经碰到的一种案例。
情况如图:
图中只截取部分,业务代码暂不展示,经排查,出问题的代码所在行是这样的:abc = append(abc, obj)
abc是一个切片。相信你基本有眉目了,没错,就是因为切片过长导致内存不够用引起的,是多大长度呢,当时崩掉时的切片长度打出来是2400万左右,这个数字大家不要死记硬背,因为每台机器上这个值是不一样的,因为机器每时每刻也运行有其它任务,剩余可用的内存肯定一直在变化中,所以即使是相同业务相同执行方式的代码,也可能是不同的结果;
因此需要充分评估代码的执行方式和数据量级影响,避免因为占用空间过大而引起内存不足,解决方式推荐以下几种:
1,可改用并发,以channel不断接收,接收端收到即处理,而不是append成切片最后才一并处理;
2,若喜欢用slice则可根据业务来分析,比如业务中需要进行好几种任务,则可以不同的切片来处理不同的数据,最后遍历这几个切片就ok(即使是顺序遍历多个切片也是很快的), 只要使用得当用slice也不是不可以;
3,灵活运用代码,根据业务判断看看map是否能用进去,如果能用map则执行方式也能有所改变。
这些都是当时想出来的可用的办法,后来采用了第一种,能有效减少空间占用、很优雅的就能解决!
另外同步一点,像内存不足这种报错,用recover()来捕获panic是捕获不到的,写的defer里的信息不会打印出来,这次案例就是印证。
如果没有这次的事情,也了解不到这种情况的优化措施,分享出来大家共勉!
如果觉得有帮助欢迎评论~