作者:叶小倩2502905191 | 来源:互联网 | 2023-05-18 09:16
Go里有函数类型的变量,这样,虽然不能在一个函数里直接声明另一个函数,但是可以在一个函数中声明一个匿名函数类型的变量,此时的匿名函数称为闭包(closure)。先看一个demo:func
Go里有函数类型的变量,这样,虽然不能在一个函数里直接声明另一个函数,但是可以在一个函数中声明一个匿名函数类型的变量,此时的匿名函数称为闭包(closure)。
先看一个demo:
func f(i int) func() int {
return func() int {
i++
return i
}
}
函数f返回了一个函数,返回的这个函数就是一个闭包。这个函数中本身是没有定义变量i的,而是引用了它所在的环境(函数f)中的变量i。
我们再看一下效果:
c1 := f(0)
c2 := f(0)
c1()
c2()
c1 跟 c2 引用的是不同的环境,在调用 i++ 时修改的不是同一个 i,因此两次的输出都是 1。函数 f 每进入一次,就形成了一个新的环境,对应的闭包中,函数都是同一个函数,环境却是引用不同的环境。
再看几个例子
package main
import "fmt"
func ExFunc(n int) func() {
sum := n
a := func() {
fmt.Println(sum + 1)
}
return a
}
func main() {
myFunc := ExFunc(10)
myFunc()
myAnotherFunc := ExFunc(20)
myAnotherFunc()
myFunc()
myAnotherFunc()
}
另一个例子:
package main
import "fmt"
func ExFunc(n int) func() {
return func() {
n++
fmt.Println(n)
}
}
func main() {
myFunc := ExFunc(10)
myFunc()
myAnotherFunc := ExFunc(20)
myAnotherFunc()
myFunc()
myAnotherFunc()
}
由此得出以下两点
1.内函数对外函数 的变量的修改,是对变量的引用
2.变量被引用后,它所在的函数结束,这变量也不会马上被烧毁
闭包函数出现的条件:
1.被嵌套的函数引用到非本函数的外部变量,而且这外部变量不是“全局变量”;
2.嵌套的函数被独立了出来(被父函数返回或赋值 变成了独立的个体),而被引用的变量所在的父函数已结束.