Golang中defer的执行时机

1.defer的执行顺序

底层是采用栈

func func1()  {
	fmt.Println("A")
}

func func2()  {
	fmt.Println("B")
}
func func3()  {
	fmt.Println("C")
}
func main()  {
 	defer func1()
	defer func2()
	defer func3()
}

输出 C B A
在这里插入图片描述

2.defer和return 的顺序

在Go语言的函数中return语句在底层并不是原子操作,它分为给返回值赋值和RET指令两步。而defer语句执行的时机就在返回值赋值操作后,RET指令执行前。具体如下图所示:defer执行时机
一 .

func  f1() int  {
  x := 5
  defer func() {
    x++
  }()
  return  x
}

输出 5

f1()函数没有命名返回值。

  1. 返回值开辟了一块新的内存空间0x aaaaa某某,未命名。赋值为5
  2. 运行defer x=6 ,这里x跟返回值已经没有关系了
  3. ruturn 是指向0x aaaaa 这片区域的值

二.

func  f1() (x int)  {
  defer func() {
    x++
  }()
  return 5
}

输出 6

f1()函数命名返回值x。

  1. 返回值开辟了一块新的内存空间0x aaaaa,赋值为x=5

  2. 运行defer x=6 。同时修改了指向0x aaaaa的值

  3. return 指向0x aaaaa区域的值

三.

func  f1() (y int)  {
  x := 5
  defer func() {
    x++
  }()
  return x
}

输出 5

f1()函数命名返回值y。

  1. 返回值开辟了一块新的内存空间0x aaaaa,赋值为y=5

  2. 运行defer x=6 。

  3. return 指向0x aaaaa区域的值

四 .

func  f1() (x int)  {
  defer func(x int ) {
    x++
  }(x)
  return 5
}

输出 5

f1()函数命名返回值x。

  1. 返回值开辟了一块新的内存空间0x aaaaa,赋值为x=5

  2. 运行defer , 通过参数传入。这里参数是新开辟的地址, 修改不了0x aaaaa下的x值

  3. return 指向0x aaaaa区域的值

  • 6
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值