在带有指针的函数循环中调用的 Goroutine 会覆盖值吗?

标签 go

我刚刚开始使用 Go,偶然发现了如何用这种语言处理指针的问题。

我有这样的代码,但不知道如何修复它以获得正确的响应。

func (me *Str) Start() 更改为 func (me Str) Start() 可以解决问题,但我需要它作为编写此结构的引用(其中会有 channel )。

示例代码(https://play.golang.org/p/EsPejyCrX7):

package main

import (
    "fmt"
    "sync"
)

var wg1 sync.WaitGroup

type Str struct {
    id int
}

func (me *Str) Start() {
    wg1.Add(1)
    fmt.Println("F1 ", me)
    go me.startFn()
}

func (me *Str) startFn() {
    defer wg1.Done()
    fmt.Println("F2 ", me)
}

func main() {
    Fl2 := []Str{
        {1},
        {2},
        {3},
    }

    for _, fl := range Fl2 {
        fl.Start()
    }
    wg1.Wait()
}

回应:

F1  &{1}
F1  &{2}
F1  &{3}
F2  &{3}
F2  &{3}
F2  &{3}

预期响应(F2 可以是随机的):

F1  &{1}
F1  &{2}
F1  &{3}
F2  &{3}
F2  &{2}
F2  &{1}

最佳答案

Using goroutines on loop iterator variables is a common mistake.

通过范围索引而不是范围值 ( playground ) 对 Fl2 的元素调用 .Start:

for i := range Fl2 {
    Fl2[i].Start()
}

但是,输出可能仍然不完全符合您的预期, 由于 goroutine 的调度, 例如它可能是这样的:

F1  &{1}
F1  &{2}
F1  &{3}
F2  &{3}
F2  &{1}
F2  &{2}

关于在带有指针的函数循环中调用的 Goroutine 会覆盖值吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/44865693/

相关文章:

windows - Go 编译器可以安装在 Windows 上吗?

mysql - 我必须在调用 *sql.Tx.Rollback() 之前调用 *sql.Rows.Close() 吗?

go - 隐式类型转换常量与变量

go - 在 go 中验证谷歌聊天机器人消息

linux - 在 go-inotify 中观察递归目录

mysql - 如何测试使用数据库(mysql)的 Go 代码?

concurrency - Go Memory Model文档中给出的这个例子失败的原因是什么?

json - 多个 map[string] 接口(interface)并将它们映射到多个 json 文件 GOLANG

go - 如何查看 runtime.futex 的来源?它只有 "System"作为父级

Golang web 应用程序自动构建和运行