首页 > 其他分享 >waitgroup如何其中一个协程发生错误,应该如何处理

waitgroup如何其中一个协程发生错误,应该如何处理

时间:2023-12-07 14:34:20浏览次数:43  
标签:wg waitgroup 协程 错误 errCh sync 如何 通道

等待一个协程组全部正确完成则结束;但其中一个协程发生错误,这时候就会阻塞,全部停止运行(本次任务失败)以免浪费系统资源,此时可以结合通道(channel)或者 select 语句两种方式来处理。

1、考虑使用两个通道:一个用于报告错误,另一个用于通知所有协程停止。在协程内部捕获错误,并将错误信息发送到错误通道。另一个协程监听错误通道,一旦有错误发生,就会向停止通知通道发送信号,通知所有协程停止运行。

 

package main

import (
    "fmt"
    "sync"
)

func worker(id int, errCh chan error, wg *sync.WaitGroup) {
    defer wg.Done()

    // 模拟错误
    if id == 2 {
        errCh <- fmt.Errorf("error occurred in worker %d", id)
        return
    }

    // 做一些工作
    fmt.Printf("Worker %d is working...\n", id)
}

func main() {
    var wg sync.WaitGroup
    errCh := make(chan error)
    stopCh := make(chan struct{})

    for i := 0; i < 5; i++ {
        wg.Add(1)
        go worker(i, errCh, &wg)
    }

    go func() {
        err := <-errCh
        if err != nil {
            fmt.Println("Error occurred:", err)
            close(stopCh)
        }
    }()

    go func() {
        wg.Wait()
        close(errCh)
    }()

    // 等待通知,停止所有协程
    <-stopCh
    fmt.Println("All workers stopped.")
}

 

errCh 通道用于发送错误信息,stopCh 通道用于通知所有协程停止。如果有一个协程发生错误,就会关闭 stopCh 通道,通知其他协程停止运行。

 

2、select 语句是 Go 中用于多路非阻塞的关键字,可以用于监听多个通道的操作。你可以在 select 语句中组合使用 WaitGroup 和通道来实现对协程组的控制。

 

package main

import (
    "fmt"
    "sync"
)

func worker(id int, errCh chan error, wg *sync.WaitGroup) {
    defer wg.Done()

    // 模拟错误
    if id == 2 {
        errCh <- fmt.Errorf("error occurred in worker %d", id)
        return
    }

    // 做一些工作
    fmt.Printf("Worker %d is working...\n", id)
}

func main() {
    var wg sync.WaitGroup
    errCh := make(chan error)

    for i := 0; i < 5; i++ {
        wg.Add(1)
        go worker(i, errCh, &wg)
    }

    go func() {
        wg.Wait()
        close(errCh)
    }()

    for {
        select {
        case err, ok := <-errCh:
            if ok {
                fmt.Println("Error occurred:", err)
                // 处理错误,根据需要执行相关操作
            } else {
                fmt.Println("All workers completed successfully.")
                return
            }
        }
    }
}

 

select 语句监听 errCh 通道,等待错误消息。当收到错误消息时,可以根据需要执行相应的错误处理。当 errCh 通道关闭时,ok 的值为 false,表示所有协程已经成功完成。

 

标签:wg,waitgroup,协程,错误,errCh,sync,如何,通道
From: https://www.cnblogs.com/beatle-go/p/17881910.html

相关文章

  • 响应式编程又变天了?看JDK21虚拟线程如何颠覆!
    本文解释为啥会有响应式编程,为什么它在开发者中不太受欢迎,以及引入Java虚拟线程后它可能最终会消失。命令式风格编程一直深受开发者喜爱,如if-then-else、while循环、函数和代码块等结构使代码易理解、调试,异常易追踪。然而,像所有好的东西一样,通常也有问题。这种编程风格导致......
  • CentOS上的HTTPS:如何设置安全的HTTPS连接
    在CentOS系统上设置安全的HTTPS连接是保护你的网站和用户数据的关键步骤。通过使用HTTPS,你可以加密与用户的通信,并确保数据在传输过程中的安全性。以下是设置安全的HTTPS连接的步骤概述:1. 获取SSL证书:首先,你需要获取一个有效的SSL证书,以验证你的网站身份并加密与用户的通信。你可......
  • 如何导出docker镜像
    参考资料:[实现本地镜像的导入、导出]我们知道docker高手制作docker镜像都是通过Dockfile去“编译”一个镜像的,但是由于种花家的网络状况,使用Dockerfile很难一步把docker里的环境给一步配好,所以更多的时候我会选择以一个base镜像为基础,装好环境后导出。就我的理解这......
  • 如何写好一篇小论文
    查阅相关文献,大量阅读相关文献。阅读文献是写作的关键,所以必须首先阅读,看看前人已经做了哪些工作,我们还可以做哪些工作。总结文章的主题。抓住每篇文章的关键,认真总结,提炼出自己想要的内容,这是自己阅读的目的,提炼要有主旨,要有层次。总结自己想要表达的观点。任何一篇文章都要有自......
  • 深入解析LLaMA如何改进Transformer的底层结构
    本文分享自华为云社区《大语言模型底层架构你了解多少?LLM大底层架构之LLM模型结构介绍》,作者:码上开花_Lancer。当前绝大多数大语言模型结构都采用了类似GPT架构,使用基于Transformer架构构造的仅由解码器组成的网络结构,采用自回归的方式构建语言模型。但是在位置编码、层归一化......
  • 使用函数计算,数禾如何实现高效的数据处理?
    作者|邱鑫鑫,王彬,牟柏旭公司背景和业务数禾科技以大数据和技术为驱动,为金融机构提供高效的智能零售金融解决方案,服务银行、信托、消费金融公司、保险、小贷公司等持牌金融机构,业务涵盖消费信贷、小微企业信贷、场景分期等多个领域,提供营销获客、风险防控、运营管理等服务。数禾科......
  • 深入解析LLaMA如何改进Transformer的底层结构
    本文分享自华为云社区《大语言模型底层架构你了解多少?LLM大底层架构之LLM模型结构介绍》,作者:码上开花_Lancer。大语言模型结构当前绝大多数大语言模型结构都采用了类似GPT架构,使用基于Transformer架构构造的仅由解码器组成的网络结构,采用自回归的方式构建语言模型。但是在位......
  • CSS如何给字体加边框
    <h1>字体边框</h1>h1{background-color:black;font-family:"Raleway",sans-serif;font-size:28px;color:red;//下方是加边框的内容text-shadow:4px4px0white,4px-4px0white,-4px-4px0white,-4px4px0white,4px3px0w......
  • 【养生】口淡、口苦、口咸、口酸,该如何调理
    从别处借鉴,以便自己方便查阅嘴巴里莫名其妙有怪怪的感觉,有时偏淡,有时却又偏苦,还会感觉酸酸的或者咸咸的,这是怎么回事呢?中医认为,如果嘴里突然出现口淡、口苦、口酸、口咸等不舒服的感觉,其实是在提醒你,身体该调理啦! 1.口淡:脾胃虚弱口淡多见于久病脾胃虚寒患者,外科大手术后病人......
  • 如何给Fedora做本地化贡献
    闲来无事,想给开源做做贡献。本来打算搞代码,但是源码下载下来,光下载编译依赖就要半天,代码又多,懒得看,就先看看有没有什么简单的。翻译倒是简单,我英语还行,所以先做做本地化看看。我用的Linux系统是Fedora,因为它安装起来很方便,可以轻松和Win11双系统,所以我就在Fedora官网上面逛。发......