关于函数闭包的疑问

Question:

  • 为何输出都为 4,不应该是 0,1,2,3 吗,每次执行的 4 是怎么来的呢
  • [4] func (){},数组中的 4 是指 4 个匿名函数吗
  • fs[i] = func() {fmt.Println("打印i = ", i)} 这句赋值会执行打印吗
  • [4]func(){} 中的数值该大或者改小为什么会出现问题呢,小则都不执行报 goroutine ,增大则会执行且报 goroutine
  • [4]func(){} 为什么不能定义成一个 slice

Code:

package main
import "fmt"
func main() {
    var fs [4]func()
    {
    }
    for i := 0; i < 4; i++ {
        fs[i] = func() {
            fmt.Println("打印i = ", i)
        }
    }

    for _, f := range fs {
        f()
    }
}

Outpit:
打印i =  4
打印i =  4
打印i =  4
打印i =  4

进程 已完成,退出代码为 0

望指点#

Mericustar
最佳答案

闭包捕获的是你外部 for 里面的局部变量 i,i 迭代 4 次之后值为 4,然后执行闭包就输出 i,也就是 4

2年前 评论
Mericustar (作者) 2年前
Scrooge (楼主) 2年前
Mericustar (作者) 2年前
Scrooge (楼主) 2年前
讨论数量: 7
Mericustar

闭包捕获的是你外部 for 里面的局部变量 i,i 迭代 4 次之后值为 4,然后执行闭包就输出 i,也就是 4

2年前 评论
Mericustar (作者) 2年前
Scrooge (楼主) 2年前
Mericustar (作者) 2年前
Scrooge (楼主) 2年前

喔,这种打印的话,是打印的最后的全局变量的 i,就是最后结束的 i 值,要打印 0 到 3 得用闭包

2年前 评论

变量作用域和函数调用环境的问题,换成下面这个才是你要的

        fs[i] = (func(i int) func() {
            return func() {
                fmt.Println("打印i = ", i)
            }
        })(i)
2年前 评论