3

考虑来自http://www.golang-book.com/10/index.htm#section2的乒乓球示例。

package main

import (
    "fmt"
    "time"
)

func pinger(c chan string) {
    for i := 0; ; i++ {
        c <- "ping"
    }
}

func ponger(c chan string) {
    for i := 0; ; i++ {
        c <- "pong"
    }
}

func printer(c chan string) {
    for {
        msg := <- c
        fmt.Println(msg)
        time.Sleep(time.Second * 1)
    }
}

func main() {
    var c chan string = make(chan string)

    go pinger(c)
    go ponger(c)
    go printer(c)

    var input string
    fmt.Scanln(&input)
}

作者写道:

“该程序现在将轮流打印乒乓球。”

但是,要做到这一点,Go 必须决定发送者可以发送到通道的顺序吗?否则,将无法保证 ping 会在 pong 之前发送(即您无法获得两个 ping 或连续两个 pong)。这是如何运作的?

4

2 回答 2

7

ping和goroutine之间没有同步pong,因此不能保证响应会按顺序打印。

如果你强制 goroutine 与 GOMAXPROCS>1 竞争,你会得到随机输出:

pong
ping
ping
pong
ping
pong
ping
pong
pong

这甚至不是“乒乓”的例子,因为没有呼叫和响应。

于 2015-03-16T22:30:32.723 回答
1

最近有一个关于进入频道的消息选择顺序的相关问题

答案是顺序通常是不确定的。这是故意的。

于 2015-03-17T21:29:41.823 回答