Go语言闭包函数的用法
在 Go 语言中,引用外部变量的函数称为闭包,即使已经离开了引用环境也不会被释放或者删除,在闭包中可以继续使用这个变量,简单可以理解为:
图 1 闭包组合方式
如果单从概念上理解闭包是十分困难的,我们不妨结合实例进行分析,代码如下:
1) 自定义函数 adder() 实现闭包功能,函数内部定义变量 x 和匿名函数,并且匿名函数作为函数返回值。
2) 匿名函数设置参数 y 和引用自定义函数 adder() 的变量 x,在匿名函数内部对变量 x 进行赋值计算,最后将变量 x 的值作为返回值。
3) 在主函数 main() 中调用函数 adder(),函数返回值以变量 f 表示,变量 f 是匿名函数的函数变量,通过函数变量 f 完成匿名函数的调用。
4) 由于函数变量 f 是调用函数 adder() 产生的,当函数变量 f 调用匿名函数时,匿名函数能使用函数 adder() 定义的变量 x。
5) 从代码的 f(10) 看到,第一次调用匿名函数的时候,变量 x 的初始值为 10,参数 y 的值设为 10,所以程序输出 20;第二次调用匿名函数的时候,变量 x 的值经过第一次调用已经变为 20,参数 y 的值设为 20,所以程序输出 40。函数变量 f 每调用一次都会改变变量 x 的值。
6) 匿名函数除了使用函数 adder() 定义的变量 x 之外,还可以使用函数 adder() 的参数作为引用环境。
根据闭包原理可以实现很多实用性功能,比如在 Web 开发中,某些网页需要用户登录才能查看,用户登录验证可以使用闭包实现。
函数+引用环境=闭包同一个函数与不同引用环境组合可以形成不同的实例,如下图所示。
图 1 闭包组合方式
如果单从概念上理解闭包是十分困难的,我们不妨结合实例进行分析,代码如下:
package main import "fmt" // 闭包 = 函数 + 引用环境 func adder() func(int) int { // 定义函数adder(),返回值为匿名函数func(int) int var x int = 10 // 匿名函数作为函数返回值 return func(y int) int { x += y return x } } func main() { // 函数adder()是一个闭包 // 函数adder()内部有变量x(引用环境)和匿名函数 // 匿名函数引用了其外部作用域中的变量x // 在函数adder()的生命周期内,变量x一直有效 f := adder() fmt.Println(f(10)) fmt.Println(f(20)) f1 := adder() fmt.Println(f1(2000)) fmt.Println(f1(5000)) }运行上述代码,运行结果为:
20
40
2010
7010
1) 自定义函数 adder() 实现闭包功能,函数内部定义变量 x 和匿名函数,并且匿名函数作为函数返回值。
2) 匿名函数设置参数 y 和引用自定义函数 adder() 的变量 x,在匿名函数内部对变量 x 进行赋值计算,最后将变量 x 的值作为返回值。
3) 在主函数 main() 中调用函数 adder(),函数返回值以变量 f 表示,变量 f 是匿名函数的函数变量,通过函数变量 f 完成匿名函数的调用。
4) 由于函数变量 f 是调用函数 adder() 产生的,当函数变量 f 调用匿名函数时,匿名函数能使用函数 adder() 定义的变量 x。
5) 从代码的 f(10) 看到,第一次调用匿名函数的时候,变量 x 的初始值为 10,参数 y 的值设为 10,所以程序输出 20;第二次调用匿名函数的时候,变量 x 的值经过第一次调用已经变为 20,参数 y 的值设为 20,所以程序输出 40。函数变量 f 每调用一次都会改变变量 x 的值。
6) 匿名函数除了使用函数 adder() 定义的变量 x 之外,还可以使用函数 adder() 的参数作为引用环境。
根据闭包原理可以实现很多实用性功能,比如在 Web 开发中,某些网页需要用户登录才能查看,用户登录验证可以使用闭包实现。