为了账号安全,请及时绑定邮箱和手机立即绑定

所有 go 例程都睡着了 - 死锁

所有 go 例程都睡着了 - 死锁

Go
拉丁的传说 2021-11-29 19:42:49
我不明白为什么在这段代码中会发生死锁。我尝试了几种不同的方法来停止僵局(使用 WorkGroup 的几个不同版本)。这是我在 Go 的第一天,到目前为止,我对相当简单直接的操作的复杂性感到非常失望。我觉得我错过了一些大而明显的东西,但是我在这方面找到的所有文档似乎都与对我来说非常基本的操作模式非常不同。所有的文档都使用原始类型的通道(int、string)而不是更复杂的类型,所有这些都带有非常基本的 for 循环,或者它们位于频谱的另一端,其中函数是相当复杂的编排。我想我真的在寻找使用 goroutines 的“这通常是如何完成的”的中间样本。package mainimport "fmt"//import "sync"import "time"type Item struct {    name string}type Truck struct {    Cargo []Item    name  string}func UnloadTrucks(c chan Truck) {    for t := range c {        fmt.Printf("%s has %d items in cargo: %s\n", t.name, len(t.Cargo), t.Cargo[0].name)    }}func main() {    trucks := make([]Truck, 2)    ch := make(chan Truck)    for i, _ := range trucks {        trucks[i].name = fmt.Sprintf("Truck %d", i+1)        fmt.Printf("Building %s\n", trucks[i].name)    }    for t := range trucks {        go func(tr Truck) {            itm := Item{}            itm.name = "Groceries"            fmt.Printf("Loading %s\n", tr.name)            tr.Cargo = append(tr.Cargo, itm)            ch <- tr        }(trucks[t])    }    time.Sleep(50 * time.Millisecond)    fmt.Println("Unloading Trucks")    UnloadTrucks(ch)    fmt.Println("Done")}
查看完整描述

1 回答

?
翻翻过去那场雪

TA贡献2065条经验 获得超13个赞

你永远不会关闭“卡车”频道ch,所以UnloadTrucks永远不会回来。


您可以在所有工作人员完成后关闭通道,使用 WaitGroup:


go func() {

    wg.Wait()

    close(ch)

}()

UnloadTrucks(ch)

http://play.golang.org/p/1V7UbYpsQr


查看完整回答
反对 回复 2021-11-29
  • 1 回答
  • 0 关注
  • 176 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信