go源码分析之defer

延迟语句defer

go版本 go1.14

defer的语义

defer会在函数返回、产生恐慌或者 runtime.Goexit 时被调用

defer的类型

在14版本中,有三种类型的defer:
在堆上分配的defer
在栈上分配的defer
开放编码式defer

// src/cmd/compile/internal/gc/ssa.go
func (s *state) stmt(n *Node) {
	/.../
	switch n.Op {
		case ODEFER:
	/../
		if s.hasOpenDefers {//开放编码式
			s.openDeferRecord(n.Left)
		} else {
			d := callDefer // 在堆上分配
			if n.Esc == EscNever {
				d = callDeferStack //在栈上分配
			}
			s.call(n.Left, d)
		}
在堆上分配的defer

使用场景: 在循环语句种使用了defer, 或者无法执行更高阶的编译器优化
优点:在编译器
缺点:需要最多的运行时支持, 占用的运行时开销最大

在栈上分配的defer

使用场景:
defer 还可以直接在栈上进行分配,也就是第二种记录 defer 的形式 deferprocStack。 在栈上分配 defer 的好处在于函数返回后 _defer 便已得到释放, 不再需要考虑内存分配时产生的性能开销,只需要适当的维护 _defer 的链表即可。

开放编码式

//todo

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值