go中for?range的坑以及解決方案
一、for range的坑
相信小伙伴都遇到過(guò)以下的循環(huán)變量的問(wèn)題,那是因?yàn)檠h(huán)的val變量是重復(fù)使用的,即僅有一份。也就是說(shuō),每次循環(huán)后賦給val的值就會(huì)把前面循環(huán)賦給val的值替換掉,所以打印出來(lái)的值都是最后一次循環(huán)賦給val的值。
1、例子
func fr1() {
arr := []int{1, 2, 3}
for _, val := range arr {
go func() {
time.Sleep(time.Millisecond * 100)
fmt.Println(val)
}()
}
time.Sleep(time.Second)
}
//輸出結(jié)果:3 3 3
func fr2() {
arr := [2]int{1, 2}
arrnew := []*int{}
for _, val := range arr {
arrnew = append(arrnew, &v)
}
fmt.Println(*arrnew[0], *arrnew[1])
//輸出結(jié)果: 2 2
}2、解決方案
使用局部變量/臨時(shí)變量,即可解決
func fr1() {
values := []int{1, 2, 3, 4, 5}
for _, val := range values {
//在這加入臨時(shí)變量
val := val
go func() {
time.Sleep(time.Millisecond * 100)
fmt.Println(val)
}()
}
time.Sleep(time.Second)
}
//輸出結(jié)果:2 3 1 4 5 或 5 3 4 1 2 等無(wú)序結(jié)果
//===========================或者=============================
func fr1() {
values := []int{1, 2, 3, 4, 5}
for _, val := range values {
//傳入變量
go func(val int) {
time.Sleep(time.Millisecond * 100)
fmt.Println(val)
}(val)
}
time.Sleep(time.Second)
}
//輸出結(jié)果:2 3 1 4 5 或 5 3 4 1 2 等無(wú)序結(jié)果二、官方解決方案
1、在Go1.21版本中,提前體驗(yàn)
可以設(shè)置 GOEXPERIMENT=loopvar,就會(huì)解決以上問(wèn)題,運(yùn)行代碼時(shí)就不會(huì)出現(xiàn)以上的坑。
Windows中設(shè)置舉例
go env -w GOEXPERIMENT=loopvar 或 $env:GOEXPERIMENT="loopvar"
> go env set GO111MODULE=on set GOARCH=amd64 set GOBIN= set GOCACHE=C:\Users\Administrator\AppData\Local\go-build set GOENV=C:\Users\Administrator\AppData\Roaming\go\env set GOEXE=.exe set GOEXPERIMENT=loopvar set GOFLAGS= set GOHOSTARCH=amd64 set GOHOSTOS=windows set GOINSECURE= set GOMODCACHE=C:\Users\Administrator\go\pkg\mod
2、預(yù)計(jì)在 Go1.22 起,在go.mod中支持
新的 for 循環(huán)語(yǔ)義,將會(huì)在 go.mod 文件中的 go 行(版本聲明大于等于 Go1.22 下)默認(rèn)應(yīng)用。也就不用設(shè)置 GOEXPERIMENT=loopvar 了
到此這篇關(guān)于go中for range的坑以及解決方案的文章就介紹到這了,更多相關(guān)go for range坑內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
GoFrame框架數(shù)據(jù)校驗(yàn)之校驗(yàn)結(jié)果Error接口對(duì)象
這篇文章主要為大家介紹了GoFrame框架數(shù)據(jù)校驗(yàn)之校驗(yàn)結(jié)果Error接口對(duì)象示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2022-06-06
golang MarshalJson的實(shí)現(xiàn)
本文主要介紹了golang MarshalJson的實(shí)現(xiàn),文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧2025-03-03
基于Go語(yǔ)言實(shí)現(xiàn)簡(jiǎn)單的計(jì)算器
這篇文章主要為大家詳細(xì)介紹了如何基于Go語(yǔ)言實(shí)現(xiàn)簡(jiǎn)單的計(jì)算器,文中的示例代碼講解詳細(xì),具有一定的學(xué)習(xí)價(jià)值,感興趣的小伙伴可以跟隨小編一起了解一下2023-10-10
Golang泛型實(shí)現(xiàn)類型轉(zhuǎn)換的方法實(shí)例
對(duì)Golang import 導(dǎo)入包語(yǔ)法詳解

