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

如果您在 Timer 频道过期后再次尝试从该频道接收会发生什么

如果您在 Timer 频道过期后再次尝试从该频道接收会发生什么

Go
守着一只汪 2022-04-20 19:25:47
我正在玩 Tour of Go 教程中的一个示例。我已将代码编辑如下:package mainimport (    "fmt"    "time")func main() {    tick := time.Tick(100 * time.Millisecond)    boom := time.After(500 * time.Millisecond)    for {        select {        case <-tick:            fmt.Println("tick.")        case <-boom:            fmt.Println("BOOM!")            c, ok := <-boom            fmt.Println(c)            fmt.Println(ok)        default:            fmt.Println("    .")            time.Sleep(50 * time.Millisecond)        }    }    fmt.Println("Finished")}但是,代码的输出如下:    .    .tick.    .    .tick.    .    .tick.    .    .tick.    .    .tick.BOOM!c并且ok永远不会打印,最后一个“完成”也永远不会打印。boom有人可以帮助我了解当我第二次尝试从频道接收时到底发生了什么?
查看完整描述

1 回答

?
慕标琳琳

TA贡献1830条经验 获得超9个赞

考虑 time.After 做了什么(引用go docs):


After 等待持续时间过去,然后在返回的通道上发送当前时间。


所以boom := time.After(500 * time.Millisecond)将返回一个通道并在 500 毫秒后向该通道发送一条消息。现在让我们考虑您的代码:


case <-boom:

   fmt.Println("BOOM!")

   c, ok := <-boom

   fmt.Println(c)

   fmt.Println(ok)

当在景气通道上接收到某些内容时,您的代码会打印“景气”,然后在景气通道上等待其他内容。但是,只有一件事会发送到繁荣通道,因此该语句c, ok := <-boom将永远不会完成(并且您的应用程序将永远不会终止)。如果您将繁荣从 a 更改为time.Aftera,time.Tick那么您可能会看到更像您期望的东西(应用程序仍将永远运行)。


原始代码有点不同:


case <-boom:

            fmt.Println("BOOM!")

            return

它接收消息,打印繁荣然后返回(结束程序)。如果您希望您的代码到达它输出“finished”的位置,那么您需要类似于下面的代码。请注意,标签loop是必需的,因为 break:


终止执行最里面的“for”、“switch”或“select”


所以没有标签 break 将退出选择,但 for 循环将继续。


package main


import (

    "fmt"

    "time"

)


func main() {

    tick := time.Tick(100 * time.Millisecond)

    boom := time.After(500 * time.Millisecond)

loop:

    for {

        select {

        case <-tick:

            fmt.Println("tick.")

        case <-boom:

            fmt.Println("BOOM!")

            break loop

        default:

            fmt.Println("    .")

            time.Sleep(50 * time.Millisecond)

        }

    }

    fmt.Println("Finished")

}


查看完整回答
反对 回复 2022-04-20
  • 1 回答
  • 0 关注
  • 124 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
微信客服

购课补贴
联系客服咨询优惠详情

帮助反馈 APP下载

慕课网APP
您的移动学习伙伴

公众号

扫描二维码
关注慕课网微信公众号