一道golang中defer和函数结合的面试题

下面代码输出什么?

package main

import "fmt"

// 下面代码输出什么?
func calc(index string, a, b int) int {
    
    
	ret := a + b
	fmt.Printf("%v,%v,%v,%v\n", 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
}

请思考,答案在下文
,
,
,
,
,
,
,
,
,
,
,
,
,
,
,


答案

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

为什么?
因为defer会先计算普通函数的值,再作为参数传入defer函数

我们将此题,稍作改变,如下,

package main

import "fmt"

// 下面代码输出什么?
func calc(index string, a, b *int) *int {
    
    
	ret := *a + *b
	fmt.Printf("%v,%v,%v,%v\n", 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
}

请思考,答案在下文















答案

10,1,2,3
20,0,2,2
2,0,2,2
1,0,3,3

为什么?与上题相比,此题改成了指针作为defer函数的参数,所以,与值传递不同


我们再看看,下面的题目

请问以下代码输出什么?为什么?

package main

import "fmt"

func main() {
    
    

	{
    
    
		defer func() {
    
    
			fmt.Println("A")
		}()
	}
	fmt.Println("B")
}




输出

B
A

请问以下代码输出什么?为什么?


func main() {
    
    

	func(){
    
    
		defer func() {
    
    
			fmt.Println("A")
		}()
	}()
	fmt.Println("B")
}




输出

A
B

defer函数是向当前函数进行注册,作用域是当前函数。第1个例子就好理解了。

第2个例子,因为是个闭包,“当前函数”就是闭包,当闭包完成之后,defer注册的函数就会被调用。所以,先输出A

猜你喜欢

转载自blog.csdn.net/yqq1997/article/details/125956304