ホームページ  >  記事  >  バックエンド開発  >  シグナルを使用して Go で Goroutine を正常に停止するにはどうすればよいですか?

シグナルを使用して Go で Goroutine を正常に停止するにはどうすればよいですか?

Barbara Streisand
Barbara Streisandオリジナル
2024-10-28 13:23:02436ブラウズ

How to Gracefully Stop a Goroutine in Go Using Signals?

シグナルによるゴルーチンの停止

Go では、ゴルーチンは同時実行に使用される軽量のスレッドです。ただし、途中で goroutine を終了する必要があるシナリオもあるかもしれません。この記事では、シグナリング メカニズムを使用してこれを実現する方法について説明します。

提供されたコードの目標は、特定の条件 (tooLate) が true になったときに goroutine を停止することです。ただし、提案どおり 2 番目のチャネルを使用すると、読み取り時にゴルーチンが実際にブロックされます。

Select で追加チャネルを使用する

より良いアプローチには、別のチャネルを作成することが含まれます ( tooLate) を使用し、ゴルーチンで select を使用して、処理チャネル (proCh) と tooLate チャネルの両方を監視します。 tooLate がシグナルを受信すると、ゴルーチンは正常に終了できます。

<code class="go">package main

import "fmt"
import "time"

func main() {
    tooLate := make(chan struct{})
    proCh := make(chan string)

    go func() {
        for {
            fmt.Println("working")
            time.Sleep(1 * time.Second)
            select {
            case <-tooLate:
                fmt.Println("stopped")
                return
            case proCh <- "processed":
            default: // Adding default makes it non-blocking
            }
            fmt.Println("done here")
        }
    }()

    select {
    case proc := <-proCh:
        fmt.Println(proc)
    case <-time.After(1 * time.Second):
        fmt.Println("too late")
        close(tooLate)
    }

    time.Sleep(4 * time.Second)
    fmt.Println("finish\n")
}</code>

この更新されたコードでは、タイマーが期限切れになると (遅すぎることを示します)、tooLate チャネルが閉じられ、ゴルーチンにシグナルが送信されます。ゴルーチンはこのシグナルを受信し、それに応じて終了します。

sync.Cond の使用

考慮すべきもう 1 つのオプションは、シグナリングをより詳細に制御できる sync.Cond の使用です。ただし、もう少しセットアップと同期ロジックが必要です。

以上がシグナルを使用して Go で Goroutine を正常に停止するにはどうすればよいですか?の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

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