導入
複数のチャネルのうち「先に届いたほう」を処理したいことがあります。そのための構文が select です。並行処理版の switch と考えると分かりやすいでしょう。
説明
package main
import (
"fmt"
"time"
)
func main() {
fast := make(chan string)
slow := make(chan string)
go func() { time.Sleep(100 * time.Millisecond); fast <- "速い方" }()
go func() { time.Sleep(300 * time.Millisecond); slow <- "遅い方" }()
for i := 0; i < 2; i++ {
select {
case msg := <-fast:
fmt.Println("受信:", msg)
case msg := <-slow:
fmt.Println("受信:", msg)
}
}
}
select { case ... }… 複数のcase(それぞれチャネルの受信)のうち、準備ができたものが実行されます。- どれも準備できていなければ、いずれかが届くまで待ちます。
- タイムアウトを組み合わせるときは
case <-time.After(1 * time.Second):のように書きます。
select はネットワーク処理などで「応答が来たら処理、一定時間来なければ諦める」といったパターンに欠かせません。
やってみよう
上の例では、先に届く「速い方」が先に表示されます。time.Sleep の値を入れ替えると、表示の順番も入れ替わります。「準備できたチャネルから処理する」感覚をつかみましょう。
これで Go コースの入門は終わりです。基本文法から並行処理まで、Go の核となる考え方を一通りたどりました。次は Go Playground や手元の環境で、実際に go run しながら手を動かしてみてください。