Go113-defer-的性能是如何提高的

最近 Go1.13 终于发布了,其中一个值得关注的特性就是 defer 在大部分的场景下性能提升了30%,但是官方并没有具体写是怎么提升的,这让大家非常的疑惑。而我因为之前写过《深入理解 Go defer》 和 《Go defer 会有性能损耗,尽量不要用?》 这类文章,因此我挺感兴趣它是做了什么改变才能得到这样子的结果,所以今天和大家一起探索其中奥妙。 原文地址:Go1.13 defer 的性能是如何提高的? 一、测试Go1.12$ go test -bench=. -benchmem -run=nonegoos: darwingoarch: amd64pkg: github.com/EDDYCJY/awesomeDeferBenchmarkDoDefer-4 20000000 91.4 ns/op 48 B/op 1 allocs/opBenchmarkDoNotDefer-4 30000000 41.6 ns/op 48 B/op 1 allocs/opPASSok github.com/EDDYCJY/awesomeDefer 3.234sGo1.13$ go test -bench=. -benchmem -run=nonegoos: darwingoarch: amd64pkg: github.com/EDDYCJY/awesomeDeferBenchmarkDoDefer-4 15986062 74.7 ns/op 48 B/op 1 allocs/opBenchmarkDoNotDefer-4 29231842 40.3 ns/op 48 B/op 1 allocs/opPASSok github.com/EDDYCJY/awesomeDefer 3.444s在开场,我先以不标准的测试基准验证了先前的测试用例,确确实实在这两个版本中,defer 的性能得到了提高,但是看上去似乎不是百分百提高 30 %。 ...

September 7, 2019 · 3 min · jiezi

Go-defer-会有性能损耗尽量不要用

上个月在 @polaris @轩脉刃 的全栈技术群里看到一个小伙伴问 “说 defer 在栈退出时执行,会有性能损耗,尽量不要用,这个怎么解?”。 恰好前段时间写了一篇 《深入理解 Go defer》 去详细剖析 defer 关键字。那么这一次简单结合前文对这个问题进行探讨一波,希望对你有所帮助,但在此之前希望你花几分钟,自己思考一下答案,再继续往下看。 测试func DoDefer(key, value string) { defer func(key, value string) { _ = key + value }(key, value)}func DoNotDefer(key, value string) { _ = key + value}基准测试: func BenchmarkDoDefer(b *testing.B) { for i := 0; i < b.N; i++ { DoDefer("煎鱼", "https://github.com/EDDYCJY/blog") }}func BenchmarkDoNotDefer(b *testing.B) { for i := 0; i < b.N; i++ { DoNotDefer("煎鱼", "https://github.com/EDDYCJY/blog") }}输出结果: ...

June 16, 2019 · 2 min · jiezi

Golang研学如何掌握并用好defer延迟执行

defer:在函数A内用defer关键字调用的函数B会在在函数A return后执行。 先看一个基础的例子,了解一下defer的效果 func main() { fmt.Println("in main func:", foo())}func foo() int { i := 0 defer fmt.Println("in defer :", i) i = 1000 fmt.Println("in foo:", i) return i+24}这段代码运行后会打印出 in foo: 1000in defer : 0in main func: 1024变量i初始化为0,defer指定fmt.Println函数延迟到return后执行,最后main函数调用foo打印返回值。 有什么用途?函数中会申明使用很多变量资源,函数结束时,我们通常会对它们做一些处理:销毁、释放(例如数据库链接、文件句柄、流)。 一般情况下,我们会在return语句之前处理这些事情。 但是,如果函数中包含多个return,这些处理我们需要在每个return之前都操作一次,实际工作中经常出现遗漏,代码维护时也很麻烦。 例如,在不用defer的时候,代码可能会这样写: func foo(i int) int { if i > 100 { fmt.Println("不是期待的数字") return 0 } if i < 50 { fmt.Println("不是期待的数字") return 0 } return i}使用defer后,代码可以这样写 ...

May 4, 2019 · 2 min · jiezi