Go语言中defer的示例分析

本篇文章为大家展示了Go语言中defer的示例分析,内容简明扼要并且容易理解,绝对能使你眼前一亮,通过这篇文章的详细介绍希望你能有所收获。

成都创新互联公司专业为企业提供阜城网站建设、阜城做网站、阜城网站设计、阜城网站制作等企业网站建设、网页设计与制作、阜城企业网站模板建站服务,10余年阜城做网站经验,不只是建网站,更提供有价值的思路和整体网络服务。

Go语言中的defer机制。

今天我们来看一段defer 机制代码:

func calc(index string, a, b int) int {
    ret := a + b
    fmt.Println(index, a, b, ret)
    return ret
}

func main() {
    a := 1
    b := 2
    defer calc("1", a, calc("10", a, b))
    a = 0
    defer calc("2", a, calc("20", a, b))
    b = 1
}

那么你觉得这段代码的正确输出是什么呢?

我们知道的defer是按照FILO(Fisrt In Last Out)的原则进行调用的。我们按照这个规则分析可能会得出下面的结果:

20 0 2 2
2 0 2 2
10 1 2 3
1 1 3 4

但是当我们运行的时候,结果其实是下面这个:

10 1 2 3
20 0 2 2
2 0 2 2
1 1 3 4

怎么会这样呢?这就要说到官方对defer的解释了。

defer语句将函数调用推送到列表上。保存的调用列表在周围函数返回后执行。Defer通常用于简化执行各种清理操作的函数。

官方说的是会在包含defer的函数“返回”时,调用defer列表(满足FILO)。但是官方的这个并没有说清楚怎么调用。而现实情况是,defer在使用时会保存当前的所有变量,如果遇到这种变量中有函数的,会先进行函数调用得到值,然后保存下来。

defer实际步骤如下:

1. 在defer表达式的地方,会调用runtime.deferproc(size int32, fn *funcval)保存延时调用,注意这里保存了延时调用的参数
2.  在return时,先将返回值保存起来
3.  按FILO顺序调用runtime.deferreturn,即延时调用
4.  RET指令

所以在本文中执行到第一个defer时,会先计算所有的参数,并压入栈。然后到第二个defer时,再计算所有的参数,再压入栈。最后在return的时候依次把第二个的defer和第一个defer弹出。最终就是我们看到的结果。

上述内容就是Go语言中defer的示例分析,你们学到知识或技能了吗?如果还想学到更多技能或者丰富自己的知识储备,欢迎关注创新互联行业资讯频道。


分享名称:Go语言中defer的示例分析
URL网址:http://scyanting.com/article/ispdoi.html