两个goroutine在同一个频道 - 它们是如何执行的?

时间:2017-10-09 06:54:42

标签: go goroutine

当我从golang.org浏览Golang时,有一个我不明白的代码片段:

func sum(a []int, c chan int, order int) {
    sum := 0
    for _, v := range a {
        sum += v
    }
    fmt.Println(order, a)
    c <- sum // 将和送入 c
}

func main() {
    a := []int{7, 2, 8, -9, 4, 0}

    c := make(chan int)
    a1, a2 := a[:len(a)/2], a[len(a)/2:]

    go sum(a1, c, 1)
    x := <-c
    go sum(a2, c, 2)
    y := <-c
    //x := <-c
    //y := <-c
    // x, y := <-c, <-c // 从 c 中获取

    fmt.Println(x, y, x+y)
}

这是我预期的输出:

1 [7 2 8]
2 [-9 4 0]
17 -5 12

当我更改代码时:

func main() {
    a := []int{7, 2, 8, -9, 4, 0}

    c := make(chan int)
    a1, a2 := a[:len(a)/2], a[len(a)/2:]

    go sum(a1, c, 1)
    //x := <-c
    go sum(a2, c, 2)
    //y := <-c
    x := <-c
    y := <-c
    // x, y := <-c, <-c // 从 c 中获取

    fmt.Println(x, y, x+y)
}

为什么输出如下:

2 [-9 4 0] 
1 [7 2 8]
-5 17 12

2 个答案:

答案 0 :(得分:4)

事情是你错过了并发的概念 无法保证按照

调用它们的确切顺序执行函数

第一个代码段有序运行的原因是x := <-c部分 此行强制您的应用等待,直到c通道填充数据,因此第二个goroutine不会被称为

答案 1 :(得分:0)

让我帮助你。

在你的第二个场景中:

2 [-9 4 0] 
1 [7 2 8]
-5 17 12

正如你所看到的,第二个goroutine的执行速度比第一个goroutine快,结果我们得到x =第二个goroutine(-5)的结果。

当您使用 go 关键字运行函数/方法时,它以并发方式运行,这意味着主函数不会等待它执行(如果不使用 sync.WaitGroup {} 选择{} )。

您可以从文档中找到更多详细信息: https://golang.org/pkg/sync/#WaitGroup