昨天遇到的Go面试题

winnie123321 · 2018-09-14 12:56:41 · 2118 次点击 · 大约8小时之前 开始浏览    置顶
这是一个创建于 2018-09-14 12:56:41 的主题,其中的信息可能已经有所发展或是发生改变。

面试题:程序代码没问题(不是变量, 资源未释放等问题), 内存占用变得很高, 正常情况下它不应该这么高的, 请问这是什么问题, 如何解决?

我问面试官的时候, 他跟我说:资源释放的时候, 那一部分内存空间还没还给系统, 导致系统内存升高, 可以用XXX工具查看(听得不是很懂, 就只记住这句, 哪位大佬解释下)


有疑问加站长微信联系(非本文作者)

入群交流(和以上内容无关):加入Go大咖交流群,或添加微信:liuxiaoyan-s 备注:入群;或加QQ群:692541889

2118 次点击  
加入收藏 微博
6 回复  |  直到 2018-09-20 15:29:51
Demon_yl
Demon_yl · #1 · 7年之前

我知道用 pprof 可以查看内存使用情况。 但怎么分析还是一知半解的。

qianguozheng
qianguozheng · #2 · 7年之前

不懂,goroutine太多?

qianguozheng
qianguozheng · #3 · 7年之前

这个问题在我们对后台服务进行压力测试时发现,我们模拟大量的用户请求访问后台服务,这时各服务模块能观察到明显的内存占用上升。但是当停止压测时,内存占用并未发生明显的下降。花了很长时间定位问题,使用gprof等各种方法,依然没有发现原因。最后发现原来这时正常的…主要的原因有两个,

一是go的垃圾回收有个触发阈值,这个阈值会随着每次内存使用变大而逐渐增大(如初始阈值是10MB则下一次就是20MB,再下一次就成为了40MB…),如果长时间没有触发gc go会主动触发一次(2min)。高峰时内存使用量上去后,除非持续申请内存,靠阈值触发gc已经基本不可能,而是要等最多2min主动gc开始才能触发gc。

第二个原因是go语言在向系统交还内存时只是告诉系统这些内存不需要使用了,可以回收;同时操作系统会采取“拖延症”策略,并不是立即回收,而是等到系统内存紧张时才会开始回收这样该程序又重新申请内存时就可以获得极快的分配速度。

winnie123321
winnie123321 · #4 · 7年之前
qianguozhengqianguozheng #3 回复

这个问题在我们对后台服务进行压力测试时发现,我们模拟大量的用户请求访问后台服务,这时各服务模块能观察到明显的内存占用上升。但是当停止压测时,内存占用并未发生明显的下降。花了很长时间定位问题,使用gprof等各种方法,依然没有发现原因。最后发现原来这时正常的…主要的原因有两个, 一是go的垃圾回收有个触发阈值,这个阈值会随着每次内存使用变大而逐渐增大(如初始阈值是10MB则下一次就是20MB,再下一次就成为了40MB…),如果长时间没有触发gc go会主动触发一次(2min)。高峰时内存使用量上去后,除非持续申请内存,靠阈值触发gc已经基本不可能,而是要等最多2min主动gc开始才能触发gc。 第二个原因是go语言在向系统交还内存时只是告诉系统这些内存不需要使用了,可以回收;同时操作系统会采取“拖延症”策略,并不是立即回收,而是等到系统内存紧张时才会开始回收这样该程序又重新申请内存时就可以获得极快的分配速度。

这种问题应该是Go1.6版本之前的吧?? Go新版本的gc已经优化的很智能了

qianguozheng
qianguozheng · #5 · 7年之前
winnie123321winnie123321 #4 回复

#3楼 @qianguozheng 这种问题应该是Go1.6版本之前的吧?? Go新版本的gc已经优化的很智能了

那这个面试官是没有测试最新版本吧

mlzhou
mlzhou · #6 · 7年之前

目前的gc还没智能到立即释放的地步,不管哪个版本都是需要gc时间的。这种内存飙高明显存在代码方面的优化,认真写代码才是关键。

添加一条新回复 (您需要 登录 后才能回复 没有账号 ?)
  • 请尽量让自己的回复能够对别人有帮助
  • 支持 Markdown 格式, **粗体**、~~删除线~~、`单行代码`
  • 支持 @ 本站用户;支持表情(输入 : 提示),见 Emoji cheat sheet
  • 图片支持拖拽、截图粘贴等方式上传