首页 > 解决方案 > select语句的运行机制问题

问题描述

当我阅读选择部分的文档时,有些东西我真的无法理解。使用文档(以及 StackOverflow 上的答案),select 将选择一个可以运行(或不会阻止)的案例。如果有多个 case,Go 会随机选择其中一个。

因此,据我了解,以下情况应随机运行:

for {
        select {
        case <-time.After(time.Millisecond * 101):
            fmt.Println("time out1")
        case <-time.After(time.Millisecond * 100):
            fmt.Println("time out2")
        }
        time.Sleep(time.Millisecond * 50)
    }

但实际上,它总是打印timed out2

为什么只打印timed out2,我认为第一种情况也没有阻塞程序,如果golang可以知道第二种情况需要多少时间,那么将这种情况替换为哪个程序不知道多少时间的操作怎么样将花费,如 db 操作,http 请求......

所以我想,select总是返回那个最快的返回?

标签: go

解决方案


time.After()返回超时到期时将在其上发送值的通道。

所以你有一个select2case秒,其中两个来自通道的接收都是阻塞的。所以select阻塞,等到其中一个可以继续。

您的 2 个超时值不同,因此较小的一个将准备好从更早的地方接收,因此一旦超时到期,就可以立即选择这种情况。

您的循环体结束,下一次迭代开始。你创建了新的超时通道,所以同样的事情会重复。


推荐阅读