[Go言語 入門] 複数のchannelを同時に実行する。(select文)
golangで作ってみたいものがあり、golangを学び始めたので学習したことを書いていくノート。
---------------------------------------------------
サイトマップはこちら
---------------------------------------------------
第19回 複数のchannelを同時に実行する。(select)
前回の学習で、Goroutineで値を渡すには channel を使うことを学んだ。
今回は channel が複数あり、同時に実行したい場合、どのようにすればいいか学ぶ。
複数の channel を同時に実行するには「select文」を使用する。
今回は、1秒ごとにint型の「100」を送信し続けるgoroutinInt関数と、1秒ごとに文字列型の「Hello World!」を送信し続けるgoroutinString関数を並列処理する。
※time.Sleepを使用している理由は出力をわかりやすくするため。
// main.go
// 数値を送信し続ける並列処理
func goroutinInt(ch chan int) {
for {
ch <- 100
time.Sleep(1 * time.Second)
}
}
// 文字列を送信し続ける並列処理
func goroutinString(ch chan string) {
for {
ch <- "Hello World!"
time.Sleep(1 * time.Second)
}
}
main関数は以下
func main() {
chInt := make(chan int)
chStr := make(chan string)
go goroutinInt(chInt)
go goroutinString(chStr)
for {
select {
case i := <-chInt:
fmt.Println(i)
case s := <-chStr:
fmt.Println(s)
}
}
}
// 実行結果
// 100
// Hello World!
// 100
// Hello World!
// Hello World!
// 100
// Hello World!
// 100
// Hello World!
// :
// :
それぞれに channel を作成し、Goroutineへ渡している。
for文の無限ループ内にselect文を作り、caseで条件分岐すると並列処理の同時実行が可能となる。
・goroutinInt関数から「100」が送信されてきたら、変数 i で受信し出力。
・goroutinString関数から「Hello World!」が送信されてきたら、変数 s で受信し出力。
~ forループから抜け出す方法 ~
上記のプログラムに5秒後ごとにBool型の「true」を返すgoroutinBool関数を追加する。
// main2.go
// Boolを送信し続ける並列処理
func goroutinBool(ch chan bool) {
for {
ch <- true
time.Sleep(5 * time.Second)
}
}
goroutinBool関数から「true」を受信したらforループを抜け出したい。
この場合どのようにすればいいか。
ラベル付きbreak文を使う。
以下サンプル。
func main() {
chInt := make(chan int)
chStr := make(chan string)
chBool := make(chan bool)
go goroutinInt(chInt)
go goroutinString(chStr)
go goroutinBool(chBool)
LOOP:
for {
select {
case i := <-chInt:
fmt.Println(i)
case s := <-chStr:
fmt.Println(s)
case b := <-chBool:
fmt.Println(b)
break LOOP
}
}
}
// 実行結果
// 100
// Hello World!
// 100
// Hello World!
// 100
// Hello World!
// 100
// Hello World!
// 100
// Hello World!
// true
「LOOP」という名前のラベルを作り、chBool が値を受信したらループから抜け出すために、case文を追加し、break文を設置。
ここでは「LOOP」と名付けたが、ラベル名に特に決まりはない。
break文は「break ラベル」と書く!
以上