Go 语言有一个select
语句,可用于轮询多个通道并根据哪个通道首先非空来执行特定操作。
例如
select {
case a := <- chanA:
foo(a)
case b := <- chanB:
baz(b)
case c := <- chanC:
bar(c)
}
这将等到或非空,然后如果例如chanA
非空,它将读取并将结果存储在 中,然后调用。也可以添加一个子句,这意味着该语句不会在通道上等待,而是在所有通道为空时执行该子句的任何内容。chanB
chanC
chanB
chanB
b
baz(b)
default:
select
default
TChan
在 Haskell 中为 STM 实现这样的最佳方法是什么?它可以通过 if-else 链天真地完成:检查每个 chanisEmptyChan
是否为空,如果它不为空,则从中读取并调用适当的函数,或者retry
如果所有通道都为空则调用。我想知道是否会有更优雅/惯用的方式来做到这一点?
请注意,Go 的select
语句也可以在其 case 中包含 send 语句,并且只有在其通道为空时才会完成一个 send 语句。如果该功能也可以复制,那就太好了,尽管我不确定是否会有一种优雅的方式来做到这一点。
只是稍微相关,但我刚刚注意到,我不确定在哪里发布:在Control.Monad.STM页面的描述中有一个错字retry
:
“实现可能会阻塞线程,直到它读取的 TVar 之一被更新。”