golang中defer执行时机的案例分析

 更新时间:2023年11月10日 09:49:26   作者:追逐梦想之路_随笔  
这篇文章主要来通过一些案例和大家一起探讨一下golang中defer的执行时机,文中的示例代码讲解详细,对我们深入了解golang有一定的帮助,感兴趣的可以跟随小编一起学习一下

示例代码

package main
import "fmt"

func calcFunc(x int, y int) int {
	return x + y
}

func main() {
	// defer语句的执行顺序是,从右到左,逆序执行
	deferDemo()

	// deferDemo1函数
	demo1 := deferDemo1()
	fmt.Println(demo1) // 0

	// deferDemo2函数
	demo2 := deferDemo2()
	fmt.Println(demo2) // 1

	// deferDemo4
	demo4 := deferDemo4()
	fmt.Println(demo4) // 1

	// deferDemo5
	demo5 := deferDemo5()
	fmt.Println(demo5) // 1

	// deferDemo6
	demo6 := deferDemo6()
	fmt.Println(demo6) // 2

	// 难点解析
	/*
		   分析:
			defer注册顺序:
			1.defer fmt.Println("AA", calcFunc(x, calcFunc(x, y)))
			2.defer fmt.Println("BB", calcFunc(x, calcFunc(x, y)))
			defer执行顺序:
			1. fmt.Println("BB", calcFunc(x, calcFunc(x, y)))
			2. fmt.Println("AA", calcFunc(x, calcFunc(x, y)))

	*/
	x := 1
	y := 2
	// 注册的时候 x = 1, y = 2 所以执行的时候x = 1, y = 2
	defer fmt.Println("AA", calcFunc(x, calcFunc(x, y))) // calcFunc(1,1+2)  // 结果是:4
	x = 10
	// 注册的时候x = 10, y = 2 所以执行的时候x = 10, y = 2
	defer fmt.Println("BB", calcFunc(x, calcFunc(x, y))) // calcFunc(10,10+2) // 结果是:22
	y = 20

}

分析:

defer语句的执行顺序是,从右到左,逆序执行

执行deferDemo()函数时,会先执行defer语句,再执行函数体,函数体执行完后,再执行defer语句

执行结果:

开启defer
结束defer
defer语句6
defer语句5
defer语句4
defer语句3
defer语句2
defer语句1

demo:

func deferDemo() {
	fmt.Println("开启defer")
	defer func() {
		fmt.Println("defer语句1")
	}()
	defer func() {
		fmt.Println("defer语句2")
	}()
	defer func() {
		fmt.Println("defer语句3")
	}()

	defer fmt.Println("defer语句4")
	defer fmt.Println("defer语句5")
	defer fmt.Println("defer语句6")

	fmt.Println("结束defer")
}

deferDemo1执行结果是 0,延迟执行

func deferDemo1() int {
	var a int

	defer func() {
		a++
	}()

	return a
}

deferDemo2执行结果是1:原因返回匿名返回值a等待函数体内操作完成才会执行return

func deferDemo2() (a int) {
	// 步骤一先赋值
	//a = 0

	// 步骤二再执行defer语句
	defer func() {
		a++
	}()

	// 步骤三再执行函数体
	// 返回值a等待函数体内操作完成才会执行return
	return a
}

deferDemo3执行结果是1: 原因返回匿名返回值a等待函数体内操作完成才会执行return

func deferDemo3() (a int) {
	defer func() {
		a++
	}()

	return a
}

deferDemo4

func deferDemo4() int {
	x := 1

	defer func(x int) {
		x++ // 内部x和外面x不是同一个变量
	}(x)

	return x // 1
}

deferDemo5

func deferDemo5() (x int) {
	x = 1

	defer func(x int) {
		x++ // 内部x和外面x不是同一个变量
	}(x)

	return x // 1
}

deferDemo6

func deferDemo6() (x int) {
	x = 1

	defer func() {
		x++
	}()

	return x // 2
}

到此这篇关于golang中defer执行时机的案例分析的文章就介绍到这了,更多相关go defer内容请搜索脚本之家以前的文章或继续浏览下面的相关文章希望大家以后多多支持脚本之家!

相关文章

  • Golang使用第三方包viper读取yaml配置信息操作

    Golang使用第三方包viper读取yaml配置信息操作

    这篇文章主要介绍了Golang使用第三方包viper读取yaml配置信息操作,具有很好的参考价值,希望对大家有所帮助。一起跟随小编过来看看吧
    2020-12-12
  • go goroutine实现素数统计的示例

    go goroutine实现素数统计的示例

    这篇文章主要介绍了go goroutine实现素数统计,本文通过示例代码给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2022-07-07
  • 详解golang defer 闭包 匿名函数

    详解golang defer 闭包 匿名函数

    这篇文章主要介绍了golang defer 闭包 匿名函数的相关知识,本文通过示例代码给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2022-07-07
  • Go语言的匿名字段实现组合复用实例探究

    Go语言的匿名字段实现组合复用实例探究

    这篇文章主要为大家介绍了Go语言的匿名字段实现组合复用实例探究,有需要的朋友可以借鉴参考下,希望能够有所帮助,祝大家多多进步,早日升职加薪
    2024-01-01
  • golang中如何保证精度的方法

    golang中如何保证精度的方法

    本文主要介绍了golang中如何保证精度的方法,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2023-04-04
  • GoPath模式和GoMoudle模式的相爱相杀

    GoPath模式和GoMoudle模式的相爱相杀

    这篇文章主要介绍了GoPath模式和GoMoudle模式的相爱相杀,本文通过实例图文相结合给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2021-03-03
  • Golang中ringbuffer的实现与应用场景详解

    Golang中ringbuffer的实现与应用场景详解

    ringbuffer因为它能复用缓冲空间,通常用于网络通信连接的读写,虽然市面上已经有了go写的诸多版本的ringbuffer组件,但还是自己造一个吧
    2023-06-06
  • Golang排序和查找使用方法介绍

    Golang排序和查找使用方法介绍

    排序操作和查找一样是很多程序经常使用的操作。尽管一个最短的快排程序只要15行就可以搞定,但是一个健壮的实现需要更多的代码,并且我们不希望每次我们需要的时候都重写或者拷贝这些代码
    2022-12-12
  • Go结合Redis用最简单的方式实现分布式锁

    Go结合Redis用最简单的方式实现分布式锁

    本文主要介绍了Go结合Redis用最简单的方式实现分布式锁示例,文中通过示例代码介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2022-01-01
  • go语言实现两个协程交替打印

    go语言实现两个协程交替打印

    这篇文章主要介绍了go语言实现两个协程交替打印,文章主要分享了两种方法使用两个channel和使用一个channel,内容介绍详细具有一定的参考价值,需要的小伙伴可以参考一下
    2022-03-03

最新评论