zoukankan      html  css  js  c++  java
  • Go

    前言

    如果你有一个任务可以分解成多个子任务进行处理,同时每个子任务没有先后执行顺序的限制,等到全部子任务执行完毕后,再进行下一步处理。这时每个子任务的执行可以并发处理,这种情景下适合使用 sync.WaitGroup

    虽然 sync.WaitGroup 使用起来比较简单,但是一不留神很有可能踩到坑里。

    sync.WaitGroup 正确使用

    比如,有一个任务需要执行 3 个子任务,那么可以这样写:

    func main() {
    	var wg sync.WaitGroup
    
    	wg.Add(3)
    
    	go handlerTask1(&wg)
    	go handlerTask2(&wg)
    	go handlerTask3(&wg)
    
    	wg.Wait()
    
    	fmt.Println("全部任务执行完毕.")
    }
    
    func handlerTask1(wg *sync.WaitGroup) {
    	defer wg.Done()
    	fmt.Println("执行任务 1")
    }
    
    func handlerTask2(wg *sync.WaitGroup) {
    	defer wg.Done()
    	fmt.Println("执行任务 2")
    }
    
    func handlerTask3(wg *sync.WaitGroup) {
    	defer wg.Done()
    	fmt.Println("执行任务 3")
    }
    

    执行输出:

    执行任务 3
    执行任务 1
    执行任务 2
    全部任务执行完毕.
    

    sync.WaitGroup 闭坑指南

    01

    // 正确
    go handlerTask1(&wg)
    
    // 错误
    go handlerTask1(wg)
    

    执行子任务时,使用的 sync.WaitGroup 一定要是 wg 的引用类型!

    02

    注意不要将 wg.Add() 放在 go handlerTask1(&wg) 中!

    例如:

    // 错误
    var wg sync.WaitGroup
    
    go handlerTask1(&wg)
    
    wg.Wait()
    
    ...
    
    func handlerTask1(wg *sync.WaitGroup) {
    	wg.Add(1)
    	defer wg.Done()
    	fmt.Println("执行任务 1")
    }
    

    注意 wg.Add() 一定要在 wg.Wait() 执行前执行!

    03

    注意 wg.Add()wg.Done() 的计数器保持一致!其实 wg.Done() 就是执行的 wg.Add(-1)

    小结

    sync.WaitGroup 使用起来比较简单,一定要注意不要踩到坑里。

    其实 sync.WaitGroup 使用场景比较局限,仅适用于等待全部子任务执行完毕后,再进行下一步处理,如果需求是当第一个子任务执行失败时,通知其他子任务停止运行,这时 sync.WaitGroup 是无法满足的,需要使用到通知机制(channel)。

    以上,希望对你能够有所帮助。

    推荐阅读

    作者:新亮笔记(关注公众号,可申请添加微信好友)
    出处:https://www.cnblogs.com/xinliangcoder
    本文版权归作者和博客园共有,欢迎转载,但未经作者同意必须保留此段声明,且在文章页面明显位置给出原文连接,否则保留追究法律责任的权利。

  • 相关阅读:
    HTTPS的七个误解(译文)
    WebLogic 11g重置用户密码
    IT项目管理工具
    Encrypt and Decrypt
    Tomcat Introduction
    浅谈https\ssl\数字证书
    What is POID
    数字签名和数字证书
    Apache Axis2 Practice
    Web Performance Tips
  • 原文地址:https://www.cnblogs.com/xinliangcoder/p/15496080.html
Copyright © 2011-2022 走看看