Tamat Masa untuk WaitGroup.Wait(): Pendekatan Idiomatik
Dalam Go, had masa boleh ditetapkan untuk WaitGroup.Wait() untuk mengelakkan penantian yang tidak terhingga bagi pekerja yang ingkar . Berikut ialah penerokaan terperinci cara idiomatik untuk melaksanakannya dan pendekatan alternatif.
Penyelesaian Disyorkan: Menggunakan Pemasa dan Saluran
Pendekatan berikut secara meluas dianggap sebagai penyelesaian paling idiomatik:
import (
"sync"
"time"
)
func waitTimeout(wg *sync.WaitGroup, timeout time.Duration) bool {
c := make(chan struct{})
go func() {
wg.Wait()
close(c)
}()
select {
case <-c:
return false // completed normally
case <-time.After(timeout):
return true // timed out
}
}
Salin selepas log masuk
- Saluran (c) dicipta untuk memberi isyarat apabila kumpulan menunggu selesai tunggu.
- Groutine dihasilkan untuk memanggil wg.Wait() dan tutup saluran apabila selesai.
- Pernyataan pilihan mendengar sama ada saluran ditutup atau tamat masa berlaku.
- Jika saluran ditutup, fungsi akan kembali palsu, menunjukkan penyiapan biasa.
- Jika tamat masa dicapai, fungsi kembali benar, menandakan tamat masa.
Memudahkan Penyelesaian Disyorkan
Untuk pelaksanaan yang lebih mudah, pertimbangkan perkara berikut:
- Tutup saluran ke isyarat selesai dan bukannya menghantar nilai.
- Gunakan tangguh untuk menutup saluran walaupun fungsi ditamatkan lebih awal.
- Alih keluar kumpulan menunggu jika hanya satu kerja perlu menunggu.
- Gunakan tempoh masa secara langsung tanpa penukaran (cth., masa.Kedua).
Pendekatan Alternatif: Menggunakan Konteks Boleh Dibatalkan
Pendekatan alternatif melibatkan penggunaan yang boleh dibatalkan konteks:
import (
"context"
"sync/atomic"
"sync"
)
func waitWithCancel(ctx context.Context, wg *sync.WaitGroup) bool {
ctxDone := make(chan struct{})
var exited int32
go func() {
defer close(ctxDone)
wg.Wait()
atomic.StoreInt32(&exited, 1)
}()
select {
case <-ctx.Done():
return atomic.LoadInt32(&exited) == 0
case <-ctxDone:
return true
}
}
Salin selepas log masuk
- Konteks boleh batal (ctx) dibuat.
- Saluran (ctxDone) digunakan untuk memberi isyarat apabila konteks dibatalkan.
- Satu goroutine dihasilkan untuk menunggu kumpulan menunggu dan memberi isyarat kepada saluran ctxDone.
- Pernyataan pilihan mendengar sama ada konteks yang akan dibatalkan atau kumpulan tunggu untuk dilengkapkan.
- Jika konteks dibatalkan, fungsi akan kembali berdasarkan sama ada kumpulan tunggu telah pun selesai menunggu.
Atas ialah kandungan terperinci Bagaimana untuk Melaksanakan Tamat Masa untuk WaitGroup.Wait() dalam Go?. Untuk maklumat lanjut, sila ikut artikel berkaitan lain di laman web China PHP!