from https://www.cnblogs.com/tr3e/p/7995689.html
1,占位
func HeavyWork(id int) {
rand.Seed(int64(id))
interval := time.Duration(rand.Intn(3)+1) * time.Second
time.Sleep(interval)
fmt.Printf("HeavyWork %-3d cost %v\n", id, interval)
}
2,每个任务完成后向waitChan写入一个数据,在收到N个完成信号后退出
// "talk is cheap, show me the code."
func main() {
waitChan := make(chan int, 1)
for i := 0; i < N; i++ {
go func(n int) {
HeavyWork(n)
waitChan <- 1
}(i)
}
cnt := 0
for range waitChan { //是用for 读取chan,如果不读取, go func 会阻塞, 主程序for 结束时,也就是并发结束时
cnt++
if cnt == N {
break
}
}
close(waitChan)
fmt.Println("finished")
}
和这一段等效
// "talk is cheap, show me the code."
// Add 用来添加 goroutine 的个数。Done 执行一次数量减 1。Wait 用来等待结束 func main() { wg := sync.WaitGroup{} for i := 0; i < N; i++ { wg.Add(1) go func(n int) { defer wg.Done() HeavyWork(n) }(i) } wg.Wait() fmt.Println("finished") }
##########################################
超时机制
1, 超时
func main() {
ok, quit := make(chan int, 1), make(chan int, 1)
go func() {
i := 0
for {
select {
case <- quit: //如果quit成功读到数据,则进行该case处理语句,如果不给 quit 传值,则不执行
ok <- 1 //给chan ok 传值,如果没有读ok,则阻塞
return
default:
HeavyWork(i)
i++
}
}
}()
time.Sleep(5 * time.Second)
quit <- 1 //不给quit值,会
<-ok
}
原文:https://www.cnblogs.com/eiguleo/p/12968460.html