当前位置: 首页 > news >正文

Golang|协程

文章目录

    • go func 和 WaitGroup
    • 协程 v.s. 线程
    • GMP 并发模型

go func 和 WaitGroup

  • 在 Go 语言中,协程(goroutine)之间并没有严格的父子关系。一个协程中可以启动其他协程,即使启动它的协程已经结束,所启动的新协程仍会继续运行,直到自身执行完毕。
  • 但需要注意的是,main 函数运行在特殊的主协程中。一旦 main 函数返回,整个程序的运行时(runtime)也会随之退出,此时即使还有其他协程未执行完毕,也会被强制终止。
package main

import (
	"fmt"
	"time"
)

func parent() {
	for i := 'a'; i <= 'z'; i++ {
		fmt.Printf("%d\n", i)
		time.Sleep(500 * time.Microsecond)
	}
}

func child() {
	for i := 'a'; i <= 'z'; i++ {
		fmt.Printf("%c\n", i)
		time.Sleep(500 * time.Microsecond)
	}
}

func main() {
	go parent()
	go child()
	fmt.Println("main")
}


// 输出
zhengjia@MacBook-Air Sys % go run "/Users/zhengjia/Downloads/Sys/main.go"
main
  • time.Sleep(100000 * time.Microsecond) 加上这段才能保证两个go程交替运行,但是这样每次都要强行等固定时间,会造成资源浪费,能不能让两个go程执行完后自动终止runtime呢?
  • 在 Go(Golang)语言中,sync.WaitGroup 是一个用于协程(goroutine)同步的重要工具。它可以用来等待一组 goroutine 全部执行完成,常用于并发任务的控制。它通过一个计数器来跟踪未完成的任务数量,并提供简单的方法来管理这个计数器。

在这里插入图片描述

package main

import (
	"fmt"
	"sync"
	"time"
)

var (
	wg = sync.WaitGroup{}
)

func parent() {
	defer wg.Done()
	wg.Add(1)
	go child()
	for i := 'a'; i <= 'z'; i++ {
		fmt.Printf("%d\n", i)
		time.Sleep(500 * time.Microsecond)
	}
}

func child() {
	defer wg.Done()
	for i := 'a'; i <= 'z'; i++ {
		fmt.Printf("%c\n", i)
		time.Sleep(500 * time.Microsecond)
	}
}

func main() {
	wg.Add(1)
	go parent()
	
	// 匿名函数
	go func() {
		defer wg.Done()
		wg.Add(1)
		go child()
		for i := 'a'; i <= 'z'; i++ {
			fmt.Printf("%d\n", i)
			time.Sleep(500 * time.Microsecond)
		}
	}()
	
	fmt.Println("main")
	wg.Wait() // 不为0就一直阻塞
}

协程 v.s. 线程

在这里插入图片描述

在这里插入图片描述

  • go中线程和协程并不是绑定的,一个协程可能中途会换一系列内核线程去执行,这和Java、CPP有着明显区别。

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

GMP 并发模型

在这里插入图片描述

在这里插入图片描述

  • M 执行 G,但必须通过绑定一个 P 才能运行
  • P 拥有一个本地的 G 队列,将 G 分配给 M
  • 多个 G 可以由多个 M 并发执行,但同时执行的数量受限于 P 的数量

在这里插入图片描述

相关文章:

  • python-1. 找单独的数
  • 关于nacos注册的服务的ip异常导致网关路由失败的问题
  • 科技项目验收测试怎么做?验收测试报告如何获取?
  • 网安小白筑基篇六:数据库(增删改语法、表约束、查询语句、多表查询、附phppython小练习)
  • Kubernetes集群环境搭建与初始化
  • 【实战手册】8000w数据迁移实践:MySQL到MongoDB的完整解决方案
  • 蓝桥杯备赛知识点总结
  • 小白学习java第12天(下):IO流之字符输入输出
  • 联影医疗智能体 重构医疗新范式
  • 【物联网】PWM控制蜂鸣器
  • aosp13增加摄像头控制功能实现
  • C#MVC项目引用Swagger的详细步骤
  • C++指针(二)
  • DAOS系统架构-组件
  • Mamba原理及在low-level vision的工作[持续更新]
  • 14-大模型微调和训练之-Hugging Face 模型微调训练(基于 BERT 的中文评价情感分析(二分类))
  • opencv-python基础
  • 如何让老电脑运行快些(极限榨干老电脑硬件)
  • 傅利叶发布首款开源人形机器人N1:开发者可实现完整复刻
  • 科普:关系图谱中的网络特征如何输入到模型中?
  • 音乐网站开发工具/网站建设杭州
  • 用什么开源框架做网站/公司网站设计报价
  • 域名查ip地址查询/北京seo公司有哪些
  • 个人摄影网站模版/seo搜索引擎营销工具
  • rar在线解压缩网站/广告投放运营主要做什么
  • 途牛网站开发需求/网站seo视频狼雨seo教程