ホームページ >バックエンド開発 >Golang >Golang で複数のチャネルから同時にデータを効率的に読み取るにはどうすればよいですか?

Golang で複数のチャネルから同時にデータを効率的に読み取るにはどうすればよいですか?

DDD
DDDオリジナル
2024-11-08 13:44:01903ブラウズ

How to Efficiently Read Data from Multiple Channels Concurrently in Golang?

Golang での複数のチャネルからの非同期読み取り

Go では、ゴルーチンは並列プログラミングで重要な役割を果たします。多くの場合、最適なパフォーマンスを達成するには、複数のチャネルから同時にデータを読み取る必要があります。

次のシナリオを考えてみましょう: ゴルーチン numgen1 と numgen2 が、それぞれチャネル num1 と num2 に同時に数値を書き込みます。あなたのタスクは、これらのチャネルから読み取り、値を追加して結果を新しいチャネル sum に書き込む新しいゴルーチン addnum を作成することです。

最初は、次のような解決策を試みるかもしれません。

func addnum(num1, num2, sum chan int) {
    done := make(chan bool)
    go func() {
        n1 := <-num1  // Read from channel
        done <- true    // Signal completion
    }()
    n2 := <-num2  // Read from channel
    <-done        // Wait for completion
    sum <- n1 + n2  // Write to destination channel
}

ただし、このアプローチには両方のチャネルからの同時読み取りが保証されていないため、欠陥があります。

解決策: select を使用する

より効率的な解決策これには、Go の select キーワードの使用が含まれます。これにより、複数のチャネルからノンブロッキング読み取りを実行できます。

func addnum(num1, num2 <-chan int, sum chan<- int) {
    for {
        select {
        case n1 := <-num1:
            select {
            case n2 := <-num2:
                sum <- n1 + n2
            default:
                // Store value back in channel
                num1 <- n1
            }
        case n2 := <-num2:
            select {
            case n1 := <-num1:
                sum <- n1 + n2
            default:
                // Store value back in channel
                num2 <- n2
            }
        }
    }
}

このコードでは、for ループが無限に実行され、num1 または num2 のいずれかのデータを継続的にリッスンします。 1 つのチャネルでデータが受信されると、内部選択は他のチャネルから読み取ろうとします。成功すると、値が追加されて合計チャネルに送信されます。

注:

  • 方向チャネル (例: chan
  • 非ブロッキング読み取り (<-) を使用すると、利用可能なデータがない場合のブロックが回避され、同時実行性が確保されます。
  • 対応する選択ケースのときに値をチャネルに保存します。失敗してもデータ損失が防止されます。

以上がGolang で複数のチャネルから同時にデータを効率的に読み取るにはどうすればよいですか?の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

声明:
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。