Go 闭包函数

Go支持匿名函数,匿名函数可以形成闭包。闭包函数可以访问定义闭包的函数定义的内部变量。

示例1:

  1. package main
  2. import "fmt"
  3. // 这个"intSeq"函数返回另外一个在intSeq内部定义的匿名函数,
  4. // 这个返回的匿名函数包住了变量i,从而形成了一个闭包
  5. func intSeq() func() int {
  6. i := 0
  7. return func() int {
  8. i += 1
  9. return i
  10. }
  11. }
  12. func main() {
  13. // 我们调用intSeq函数,并且把结果赋值给一个函数nextInt,
  14. // 这个nextInt函数拥有自己的i变量,这个变量每次调用都被更新。
  15. // 这里i的初始值是由intSeq调用的时候决定的。
  16. nextInt := intSeq()
  17. // 调用几次nextInt,看看闭包的效果
  18. fmt.Println(nextInt())
  19. fmt.Println(nextInt())
  20. fmt.Println(nextInt())
  21. // 为了确认闭包的状态是独立于intSeq函数的,再创建一个。
  22. newInts := intSeq()
  23. fmt.Println(newInts())
  24. }

输出结果为

  1. 1
  2. 2
  3. 3
  4. 1

示例2:

  1. package main
  2. import "fmt"
  3. func main() {
  4. add10 := closure(10)//其实是构造了一个加10函数
  5. fmt.Println(add10(5))
  6. fmt.Println(add10(6))
  7. add20 := closure(20)
  8. fmt.Println(add20(5))
  9. }
  10. func closure(x int) func(y int) int {
  11. return func(y int) int {
  12. return x + y
  13. }
  14. }

输出结果为:

  1. 15
  2. 16
  3. 25

示例3:

  1. package main
  2. import "fmt"
  3. func main() {
  4. var fs []func() int
  5. for i := 0; i < 3; i++ {
  6. fs = append(fs, func() int {
  7. return i
  8. })
  9. }
  10. for _, f := range fs {
  11. fmt.Printf("%p = %v\n", f, f())
  12. }
  13. }

输出结果:

  1. 0x401200 = 3
  2. 0x401200 = 3
  3. 0x401200 = 3

示例4:

  1. package main
  2. import "fmt"
  3. func adder() func(int) int {
  4. sum := 0
  5. return func(x int) int {
  6. sum += x
  7. return sum
  8. }
  9. }
  10. func main() {
  11. result := adder()
  12. for i := 0; i < 10; i++ {
  13. fmt.Println(result(i))
  14. }
  15. }

输出结果为:

  1. 0
  2. 1
  3. 3
  4. 6
  5. 10
  6. 15
  7. 21
  8. 28
  9. 36
  10. 45