go语言循环变量
阅读go语言圣经第五章第六节介绍到了捕获迭代变量
package main
import (
"fmt"
)
func main() {
var lis []func()
for i := 0; i < 10; i++ {
lis = append(lis, func() {
fmt.Println(i)
})
}
for _, f := range lis {
f()
}
}
这段代码执行结果是打印了10个10
出现这个结果的原因是for循环的循环体会共享循环变量i的值,因此第二个for循环开始调用f函数时,他们的i共享的是最后一次的循环变量i的值,此时i已经变成了10。
如何确保函数打印循环到某一时刻的i值呢?
package main
import (
"fmt"
)
func main() {
var lis []func()
for i := 0; i < 10; i++ {
i := i
lis = append(lis, func() {
fmt.Println(i)
})
}
for _, f := range lis {
f()
}
}
以上代码实现该效果。我的理解是:i:=0;i<10;i++是一个词法块,它是for循环体的上一级作用域,原来的for循环体找i是从上级作用域找到的。所以,只要我们能让for循环体找i时从自己的作用域找就可以了,因此,我们需要在循环体内重新声明一个变量保存上级作用域中的i在当前循环的值。这里我声明的变量还是i(go语言圣经也用原变量名,应该是让读者记忆更深刻吧)
浙公网安备 33010602011771号