🌷🍁 博主猫头虎(🐅🐾)带您 Go to New World✨🍁
🦄 博客首页——🐅🐾猫头虎的博客🎐
🐳 《面试题大全专栏》 🦕 文章图文并茂🦖生动形象🐅简单易学!欢迎大家来踩踩~🌺
🌊 《IDEA开发秘籍专栏》 🐾 学会IDEA常用操作,工作效率翻倍~💐
🌊 《100天精通Golang(基础入门篇)》 🐅 学会Golang语言,畅玩云原生,走遍大小厂~💐
🐅🐾猫头虎建议Go程序员必备技术栈一览表📖:
☁️🐳
Go语言开发者必备技术栈☸️
:
🐹 GoLang | 🌿 Git | 🐳 Docker | ☸️ Kubernetes | 🔧 CI/CD | ✅ Testing | 💾 SQL/NoSQL | 📡 gRPC | ☁️ Cloud | 📊 Prometheus | 📚 ELK Stack
🪁🍁 希望本文能够给您带来一定的帮助🌸文章粗浅,敬请批评指正!🐅🐾🍁🐥
文章目录
- 🐅🐾猫头虎建议Go程序员必备技术栈一览表📖:
- 2022年9月26日 Go生态洞察:Go运行时4年后的进展
- 摘要
- 引言
- 正文
- 🌟 Go运行时的新变化
- 1. `sync.Pool`的优化
- 2. 主动回收内存
- 3. 更灵活的goroutine抢占
- 4. 更高效的定时器管理
- 5. `defer`语句的优化
- 6. 内存分配器的改进
- 7. 更细致的内存统计API
- 8. 调度器的CPU时间优化
- 9. 基于寄存器的调用约定
- 10. GC内部会计和调度的重新设计
- 11. 空闲时限制GC的CPU使用
- 🛠️ 一个新的调节器
- 📚 结论
- 总结
- 下一篇预告
- 原创声明
-
原创作者: 猫头虎
-
作者wx: Libin9iOak
-
作者公众号: 猫头虎技术团队
2022年9月26日 Go生态洞察:Go运行时4年后的进展
🐱 猫头虎博主来啦!今天带来的是Go语言的最新动态。如果你是一个Go语言爱好者,那这篇文章一定不容错过!一起来看看自2018年以来Go运行时和Go垃圾收集器(GC)有哪些新的变化吧!🚀
摘要
🔍 在这篇文章中,作为猫头虎博主,我将带大家深入探讨自2018年以来Go运行时的发展。从sync.Pool
的优化,内存分配器的改进,到新的软内存限制功能,我们将深入每一个更新,了解它们是如何使Go语言变得更高效。准备好了吗?让我们开始吧!
引言
自2018年我们关于Go GC的上一篇博客以来,Go运行时和Go垃圾收集器(GC)有了稳步的提升。这些改进主要是为了应对现实世界中Go程序的挑战和Go用户面临的实际问题。接下来,让我们一起回顾这些年来的亮点吧!
正文
🌟 Go运行时的新变化
1. sync.Pool
的优化
- Go 1.13版本中,
sync.Pool
成为了一个对GC更友好的内存重用工具,它的延迟影响更小,并且能更有效地回收内存。
2. 主动回收内存
- Go运行时现在能更主动地将不需要的内存返还给操作系统,减少了内存消耗,降低了内存不足错误的发生几率。这降低了高达20%的闲置内存消耗。(Go 1.13 和 1.14)
3. 更灵活的goroutine抢占
- 在许多情况下,Go运行时能更容易地抢占goroutines,减少了长达90%的停止世界(stop-the-world)延迟。点击此处观看Gophercon 2020的演讲。(Go 1.14)
4. 更高效的定时器管理
- Go运行时比以前更有效地管理定时器,尤其是在多核CPU机器上。(Go 1.14)
5. defer
语句的优化
- 使用
defer
声明的函数调用现在在大多数情况下的成本与常规函数调用一样低。点击此处观看Gophercon 2020的演讲。(Go 1.14)
6. 内存分配器的改进
- 内存分配器的慢路径现在能更好地随着CPU核心数量扩展,在高并行程序中提高了高达10%的吞吐量,降低了高达30%的尾延迟。进一步阅读。(Go 1.14 和 1.15)
7. 更细致的内存统计API
- Go内存统计现在可以通过一个更细致、灵活和高效的API访问,即[runtime/metrics包](https://pkg
.go.dev/runtime/metrics)。这降低了获取运行时统计数据的延迟两个数量级(从毫秒到微秒)。(Go 1.16)
8. 调度器的CPU时间优化
- Go调度器在寻找新工作时消耗的CPU时间减少了高达30%。(Go 1.17)
9. 基于寄存器的调用约定
- 在amd64、arm64和ppc64上,Go代码现在遵循一种基于寄存器的调用约定,提高了高达15%的CPU效率。(Go 1.17 和 Go 1.18)
10. GC内部会计和调度的重新设计
- Go GC的内部会计和调度已经重新设计,解决了一系列长期存在的效率和鲁棒性问题。这对于goroutines栈占据了大量内存使用的应用程序而言,显著降低了应用程序的尾延迟(高达66%)。(Go 1.18)
11. 空闲时限制GC的CPU使用
- Go GC现在在应用程序空闲时限制了自己的CPU使用。这导致在非常空闲的应用程序中,GC周期期间的CPU利用率降低了75%,减少了可能引起作业形状混淆的CPU峰值。(Go 1.19)
🛠️ 一个新的调节器
随着Go 1.19的发布,一个期待已久的特性终于来了:Go运行时的软内存限制。
多年来,Go GC只有一个调节参数:GOGC
。GOGC
让用户调整由Go GC做出的CPU开销与内存开销之间的权衡。这个“调节器”长期以来服务于Go社区,涵盖了广泛的用例。
为什么要添加一个内存限制调节器呢?
内存与CPU时间不同,不像CPU时间那样总有未来可以等待。但对于内存来说,有一个极限。
内存限制解决了两个问题。
首先,当应用程序的峰值内存使用不可预测时,仅靠GOGC
几乎无法防止内存耗尽。仅有GOGC
时,Go运行时根本不知道它能使用多少内存。设置内存限制使得运行时能够抵抗瞬时的、可恢复的负载峰值,通过意识到何时需要更努力地减少内存开销。
其次,为了在不使用内存限制的情况下避免内存不足错误,必须根据峰值内存调整GOGC
,即使在应用程序不在峰值内存使用时也保持低内存开销,从而导致更高的GC CPU开销。这在我们这个容器化的世界尤为重要,程序被放置在具有特定和隔离的内存预留的箱子中;我们可能会更好地利用它们!通过提供对负载峰值的保护,设置内存限制允许GOGC
在CPU开销方面进行更积极的调整。
内存限制的设计旨在易于采用和鲁棒。例如,它是对应用程序Go部分的整个内存占用的限制,而不仅仅是Go堆,所以用户不必担心计算Go运行时的开销。运行时也会根据内存限制调整其内存清理政策,以便在面对内存压力时更积极地将内存返回给操作系统。
然而,尽管内存限制是一个强大的工具,但在使用时仍需小心。一个重要的注意事项是,它可能导致程序出现GC抖动:程序花费太多时间运行GC,导致无法有效地进行实质性工作。例如,如果为Go程序设置的内存限制过低,不足以满足程序实际所需的内存,那么程序可能会出现抖动。以前,除非GOGC
被明确调整为更偏重于内存使用,否则GC抖动是不太可能发生的。作为一种缓解措施,即使这意味着超出内存限制,运行时也会将GC限制在总CPU时间的50%以内。
考虑到这些,我们发布了一份全新的GC指南,其中包含互动式可视化内容,帮助您理解GC成本以及如何操纵它们。
📚 结论
尝试使用内存限制!在生产环境中使用它!阅读GC指南!
我们一直在寻求反馈,以改进Go,但同时也希望听到关于它如何有效工作的故事。发送我们反馈!
特性 | 描述 | Go版本 |
---|---|---|
sync.Pool 优化 | 低延迟影响,高效内存回收 | Go 1.13 |
主动回收内存 | 减少内存消耗,降低内存不足错误 | Go 1.13, 1.14 |
Goroutine抢占 | 减少停止世界延迟 | Go 1.14 |
定时器管理 | 在多核CPU上效率更高 | Go 1.14 |
defer 优化 | 成本接近常规函数调用 | Go 1.14 |
内存分配器 | 更好的CPU核心扩展性 | Go 1.14, 1.15 |
内存统计API | 更快的运行时统计数据访问 | Go 1.16 |
调度器CPU优化 | 减少CPU时间消耗 | Go 1.17 |
基于寄存器的调用约定 | 提高CPU效率 | Go 1.17, 1.18 |
GC内部重设计 | 减少尾延迟,提高效率 | Go 1.18 |
限制GC的CPU使用 | 减少CPU利用率 | Go 1.19 |
总结
以上就是自2018年以来Go运行时的主要进展。这些改进大多对用户来说是不可见的:他们熟悉和喜爱的Go代码,只需升级Go版本就能运行得更好。
本文被猫头虎的Go生态洞察专栏收录,详情点击这里。
下一篇预告
🔜 下一篇文章我们将探讨《Go语言十三年》——深入Go语言的发展历程,了解它是如何从一个小众语言成长为今天的热门技术。敬请期待! 点击预览
原创声明
======= ·
-
原创作者: 猫头虎
-
作者wx: Libin9iOak
-
作者公众号: 猫头虎技术团队
学习 | 复习 | Go生态 |
---|---|---|
✔ | ✔ | ✔ |
本文为原创文章,版权归作者所有。未经许可,禁止转载、复制或引用。
作者保证信息真实可靠,但不对准确性和完整性承担责任。
未经许可,禁止商业用途。
如有疑问或建议,请联系作者。
感谢您的支持与尊重。
点击
下方名片
,加入IT技术核心学习团队。一起探索科技的未来,洞察Go生态,共同成长。