我有一片整数,它们是并发操作的:
ints := []int{1, 2, 3, 4, 5, 6, 7, 8, 9, 10}
我使用缓冲 channel 作为信号量,以便获得并发运行的 go 例程的上限:
sem := make(chan struct{}, 2)
for _, i := range ints {
// acquire semaphore
sem <- struct{}{}
// start long running go routine
go func(id int, sem chan struct{}) {
// do something
// release semaphore
<- sem
}(i, sem)
}
上面的代码在达到最后一个或最后两个整数之前运行良好,因为程序在最后一个 go 例程完成之前结束。
问题:如何等待缓冲 channel 耗尽?
最佳答案
您不能以这种方式使用信号量(在本例中为 channel )。当您处理值和分派(dispatch)更多 goroutine 时,无法保证它在任何时候都不会为空。在这种情况下,这不是一个问题,特别是因为您正在同步调度工作,但是因为没有无竞争的方式来检查 channel 的长度,所以没有等待 channel 长度达到 0 的原语。
使用 sync.WaitGroup
等待所有 goroutines 完成
sem := make(chan struct{}, 2)
var wg sync.WaitGroup
for _, i := range ints {
wg.Add(1)
// acquire semaphore
sem <- struct{}{}
// start long running go routine
go func(id int) {
defer wg.Done()
// do something
// release semaphore
<-sem
}(i)
}
wg.Wait()
关于go - 如何等到缓冲 channel (信号量)为空?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/39776481/