本文共 1357 字,大约阅读时间需要 4 分钟。
目录
传统的方案是,假设一段任务在执行,我们通过设置共享内存的一个变量的值为 true 或者 false 来进行判断。现在我们将利用 CSP, 多路选择机制和 channel 的关闭与广播实现任务取消功能。
通过 CSP 在 channel 上广播一个消息,告诉所有的协程,大家现在可以停了。
通过多了选择机制,如果从 channel 上收到一个消息,代表需要执行任务取消功能,否则不执行。
package cancel_by_closeimport ( "fmt" "sync" "testing" "time")//任务是否已被取消//实现原理://检查是否从 channel 收到一个消息,如果收到一个消息,我们就返回 true,代表任务已经被取消了//当没有收到消息,channel 会被阻塞,多路选择机制就会走到 default 分支上去。func isCanceled(cancelChan chan struct{}) bool { select { case <-cancelChan: return true default: return false }}//执行任务取消//因为 close() 是一个广播机制,所以所有的协程都会收到消息func execCancel(cancelChan chan struct{}) { // close(cancelChan)会使所有处于处于阻塞等待状态的消息接收者(<-cancelChan)收到消息 close(cancelChan)}//利用 CSP, 多路选择机制和 channel 的关闭与广播实现任务取消功能func TestCancel(t *testing.T) { var wg sync.WaitGroup cancelChan := make(chan struct{}, 0) //启动 5 个协程 for i := 0; i < 5; i++ { wg.Add(1) go func(i int, cancelChan chan struct{}, wg *sync.WaitGroup) { //做一个 while(true) 的循环,一直检查任务是否有被取消 for { if isCanceled(cancelChan) { fmt.Println(i, "is Canceled") wg.Done() break; } else { //其它正常业务逻辑 time.Sleep(time.Millisecond * 5) } } }(i, cancelChan, &wg) } //执行任务取消 execCancel(cancelChan) wg.Wait()}/*=== RUN TestCancel4 is Canceled0 is Canceled1 is Canceled2 is Canceled3 is Canceled--- PASS: TestCancel (0.00s)PASS*/
注:这篇博文是我学习中的总结,如有转载请注明出处:
上一篇:
下一篇: