Golang并发编程中控制主goroutine退出实现的例子

在使用golang进行并发编程的时候,当你新起goroutine异步执行时,主goroutine并不知道其它goroutine是否运行完毕,一旦主goroutine退出后,所有的goroutine都会退出,因此需要控制主goroutine退出时间,可有如下方法:

(1)time.Sleep()

比较粗暴,不靠谱,就是让主goroutine多跑一会儿,实际并不确定其它goroutine是否运行结束.

(2)利用channel通信

在主goroutine一直阻塞等待一个退出信号,在其他goroutine完成任务后给主协程发送一个信号,主协程收到这个信号后退出

e := make(chan bool)
 go func() {
      fmt.Println("hello")
      e <- true
 }()
 <-e

(3)利用sync.WaitGroup

WaitGroup,它能够一直等到所有的goroutine执行完成,并且阻塞主线程的执行,直到所有的goroutine(Golang中并发执行的协程)执行完成。

 var wg sync.WaitGroup
     func main() {
          wg.Add(1)
          go func() {
               fmt.Println("hello")
               wg.Done() //完成
          }()
          wg.Wait()
     }

时间: 2024-10-29 08:03:57

Golang并发编程中控制主goroutine退出实现的例子的相关文章

Go并发编程中的那些事[译]

原文地址:Concurrent programming 原文作者:StefanNilsson 译文出自:掘金翻译计划 本文永久链接:github.com/xitu/gold-m- 译者:kobehaha 校对者:joyking7 alfred-zhong 本文讲的是Go并发编程中的那些事, bouncing balls 1. 多线程执行 2. Channels 3. 同步 4. 死锁 5. 数据竞争 6. 互斥锁 7. 检测数据竞争 8. Select标识符 9. 最基本的并发实例 10. 并行

简单的并发编程中犯2的一个小例子--CAS使用时一定要考虑下是否有必要做轮询

并发编程我自己写过不少文章,不过我由于其相对需要理解更多的东西,我自己写代码也有时长犯2的时候,对于这些犯2的问题,我们只能将它作为自己宝贵的经历和财富,本文是很简单Java并发方面的小文章,为啥?因为是一个犯2的例子,这里给大家做个简单分享. 先简单描述下场景: 在一个app中,我需要为访问者提供某种信息的存储,由于架构上已经确定的方式,所以可以确保每一个app上存储的用户不会太多,于是就放在了内存中,而不是缓存. 这些信息需要定期清理掉,就像会话一样,每个用户都会有一个唯一的key标识符,用

浅谈Linux环境下并发编程中C语言fork()函数的使用_C 语言

由fork创建的新进程被称为子进程(child process).fork函数被调用一次,但返回两次.子进程的返回值是0,而父进程的返回值则是新进程的进程ID.将子进程ID返回给父进程的理由是:因为一个进程的子进程可以有多个,并且没有一个函数使一个进程可以获得其所有子进程的进程ID.fork使子进程得到返回值0的理由是:一个进程只会有一个父进程,所以子进程总是可以调用getpid以获得其父进程的进程ID. 使fork失败的两个主要原因是:系统中已经有了太多的进程,或者该实际用户ID的进程总数超过

Java并发编程中使用Executors类创建和管理线程的用法_java

1. 类 ExecutorsExecutors类可以看做一个"工具类".援引JDK1.6 API中的介绍:   此包中所定义的 Executor.ExecutorService.ScheduledExecutorService.ThreadFactory 和 Callable 类的工厂和实用方法.此类支持以下各种方法: (1)创建并返回设置有常用配置字符串的 ExecutorService 的方法. (2)创建并返回设置有常用配置字符串的 ScheduledExecutorServic

Java并发编程中的阻塞和中断

>>线程的状态转换 线程的状态转换是线程控制的基础,下面这张图片非常直观的展示了线程的状态转换: 线程间的状态转换:  1. 新建(new):新创建了一个线程对象. 2. 可运行(runnable):线程对象创建后,其他线程(比如main线程)调用了该对象的start()方法.该状态的线程位于可运行线程池中,等待被线程调度选中,获取cpu 的使用权 . 3. 运行(running):可运行状态(runnable)的线程获得了cpu 时间片(timeslice) ,执行程序代码. 4. 阻塞(b

详解C++编程中的主表达式与后缀表达式编写基础_C 语言

主表达式主表达式是更复杂的表达式的构造块.它们是文本.名称以及范围解析运算符 (::) 限定的名称.主表达式可以具有以下任一形式: literal this :: name name ( expression ) literal 是常量主表达式.其类型取决于其规范的形式. this 关键字是指向类对象的指针.它在非静态成员函数中可用,并指向为其调用函数的类的实例. this 关键字只能在类成员函数体的外部使用. this 指针的类型是未特别修改 this 指针的函数中的 type *const(

C++并发编程中static变量的问题

在C++中,static表示的是"静态初始化",由其声明的变量因此也叫作"静态变量",他们从完成初始化后就一直存在于程序运行空间中(确切地说位于静态变量区),直至程序退出或销毁. 如果按照变量的作用域来划分,静态变量可以分为3类: global variable,即全局变量 static variable with file scope static variable with block scope 前两种不必多说,重点说一下第三种里的"block sc

Java并发编程中的生产者与消费者模型简述_java

概述对于多线程程序来说,生产者和消费者模型是非常经典的模型.更加准确的说,应该叫"生产者-消费者-仓库模型".离开了仓库,生产者.消费者就缺少了共用的存储空间,也就不存在并非协作的问题了. 示例定义一个场景.一个仓库只允许存放10件商品,生产者每次可以向其中放入一个商品,消费者可以每次从其中取出一个商品.同时,需要注意以下4点: 1.  同一时间内只能有一个生产者生产,生产方法需要加锁synchronized. 2.  同一时间内只能有一个消费者消费,消费方法需要加锁synchroni

Java并发编程中构建自定义同步工具_java

当Java类库没有提供适合的同步工具时,就需要构建自定义同步工具. 可阻塞状态依赖操作的结构 复制代码 代码如下: acquir lock on object state;//请求获取锁 while(precondition does not hold){//没有满足前提条件    release lock;//先释放锁    wait until precondition might hold;//等待满足前提条件    optionlly fail if interrupted or tim