go并发模型?

Go语言——goroutine并发模型

参考:

Goroutine并发调度模型深度解析手撸一个协程池

Golang 的 goroutine 是如闹没何实现的?

Golang - 调度剖析【第二部分】

OS线程初始栈为2MB。Go语言中,每个goroutine采用动态扩容方式,初始2KB,按需增长,最大1G。此外GC会收缩栈空间。

BTW,增长扩容都是有代价的,需要copy数据到新的stack,所以初始2KB可能有些性能问题。

更多关于stack的内容,可以参见大佬的文章。 聊一聊goroutine stack

用户线程的调度以及生命周期管理都是用户层面含兄,Go语言自己实现的,不借助OS系统调用,减少系统资源消耗。

Go语言采用两级线程模型,即用户线程与内核线程KSE(kernel scheduling entity)是M:N的。最终goroutine还是会交给OS线程执行,但是需要一个中介,提供上下文。这就是G-M-P模型

Go调度器有两个不同的运行队列:

go1.10\src\runtime\runtime2.go

Go调度器根据事件进行上下文切换。

调度的液老纳目的就是防止M堵塞,空闲,系统进程切换。

详见 Golang - 调度剖析【第二部分】

Linux可以通过epoll实现网络调用,统称网络轮询器N(Net Poller)。

文件IO操作

上面都是防止M堵塞,任务窃取是防止M空闲

每个M都有一个特殊的G,g0。用于执行调度,gc,栈管理等任务,所以g0的栈称为调度栈。g0的栈不会自动增长,不会被gc,来自os线程的栈。

go1.10\src\runtime\proc.go

G没办法自己运行,必须通过M运行

M通过通过调度,执行G

从M挂载P的runq中找到G,执行G

go并发模型?  第1张

Go CSP并发模型

Go的CSP并发模型

Go实现了两种并发形式。第一种是大家普遍认知的:多线程共享内存。其实就是Java或者C++等语言中的多线程开发。另外一种是Go语言特有的,也是判岁者Go语言推荐的:CSP(communicating sequential processes)并发模型。

CSP 是 Communicating Sequential Process 的简称,中文可以叫做通信顺序进程,是一掘薯种并发编程模型,由 Tony Hoare 于雀凯 1977 年提出。简单来说,CSP 模型由并发执行的实体(线程或者进程)所组成,实体之间通过发送消息进行通信,这里发送消息时使用的就是通道,或者叫 channel。CSP 模型的关键是关注 channel,而不关注发送消息的实体。 Go 语言实现了 CSP 部分理论 。

“ 不要以共享内存的方式来通信,相反, 要通过通信来共享内存。”

Go的CSP并发模型,是通过 goroutine和channel 来实现的。

goroutine 是Go语言中并发的执行单位。其实就是协程。

channel是Go语言中各个并发结构体(goroutine)之前的通信机制。 通俗的讲,就是各个goroutine之间通信的”管道“,有点类似于Linux中的管道。

Channel

Goroutine

go 的并发调度(一) GMP 模型

原文出自: Golang调度器GPM原理与调度全分析

M想要执行、放回G都必须访问全局G队列,并且M有多个,即多线程访问同一资源需要加锁进行保证互斥/同步,所以全局G队列是有互斥锁进行保护的。

老调度器有几个缺点:

面对之前调度器的问题,Go设计了新的调度器。

新的调度器引入了P的概念:Processor,它包含了运行goroutine的资源,如果线程想运行goroutine,必须先获取P,P中还包册冲租含了可运行的G队列。

这意味着在程序执行的任意州兆时刻都只有$GOMAXPROCS个goroutine在同时运行。

M与P的数量没有绝对关系,一个M阻塞,P就会去创建或者切换另一个M,所以,即使P的默认数量是1,也有可能会创建很多个M出来。

从上图我们可以分析出几个结论:

1、我们通过 go func()来创建一个goroutine;

2、有两个存储G的队列,一个是局部调度器P的本地队列、一个是全局G队列。新创建的G会先保存在P的本地队列中,如果P的本地队列已经满了就会保存在全局的队列中;

3、G只能运行在M中,一个M必须持有一个P,M与P是1:1的关系。M会从P的本地队列弹出一个可执行状态的G来执行,如果P的本地队列为空,就会想其他的MP组合偷取一个可执行的G来执行;

4、一个M调度G执行的过程是一个循环机制;

5、当M执行某一个G时候如果发生了syscall或则其余阻塞操作,M会阻塞,如果当前有一些G在执行,runtime会把这个线程M从P中摘除(detach),然后再创建一个新的操作系统的线程(如果有空闲的线程可用就复用空闲线程)来服务于这个P;

6、当M系统调用结束时候,这个G会尝试获取一个空闲的P执行,并放入到这个P的本地队列。如果获取不到P,那么这个线程M变成休眠状态, 加入到空闲判羡线程中,然后这个G会被放入全局队列中。

以上内容为新媒号(sinv.com.cn)为大家提供!新媒号,坚持更新大家所需的互联网后端知识。希望您喜欢!

版权申明:新媒号所有作品(图文、音视频)均由用户自行上传分享,仅供网友学习交流,不声明或保证其内容的正确性,如发现本站有涉嫌抄袭侵权/违法违规的内容。请发送邮件至 k2#88.com(替换@) 举报,一经查实,本站将立刻删除。

(0)
上一篇 2023-09-23 14:26
下一篇 2023-09-23 14:26

相关推荐

  • nft上怎么抢首发?

    支付宝抢NFT作品有什么诀窍吗 没有诀窍。 支付宝nft的交易方法如下: 1、打开手机支付宝,点击首页上方的搜索栏。 2、输入nft后点击搜索,在搜索结果中点击我的NFT。 3、进...

    2023-03-08
  • 玩nft起什么名字,nft游戏有哪些

    字节跳动nft平台名字 2022年10月1日字节跳动旗下的TikTok宣布推出首个NFT系列——TikTok Top Moments 国内目前比较火的NFT交易平台有阿里巴巴旗下的...

    2023-03-08
  • 什么是区块链的高度?

    什么叫做区块链 区块链是什么意思?区块链是一种分布式数据库技术,它可以记录交易、支付和其他金融交易,以及其他非金融交易,并使用加密技术进行安全保护。区块链可以被认为是一种分布式账本...

    2023-09-22
  • 机器人编程入门培训?

    机器人编程怎么入门 1、先学习C语言,这是基础,然后学习单片机,然后就是实验步进电机的控制,译码器的工作原理和编程等等,这些是入门,有基础之后可以学点Arduino之类的,了解当前...

    2023-09-24
  • map的value转list(map中的value类型转换)

    map的value是arraylist怎么取出里面的值? 1、但对于iterator的remove()方法,也有需要我们注意的地方。每调用一次iterator.next()方法,只...

    2023-09-23
  • python官网是多少

    导读:今天首席CTO笔记来给各位分享关于python官网是多少的相关内容,如果能碰巧解决你现在面临的问题,别忘了关注本站,现在开始吧! 请问,python官网是pythonf.co...

  • 区块链智慧工程是什么(区块链接智能)

    什么是区块链 区块链工程专业是学什么的 区块链是一个信息技术领域的术语。从本质上讲,它是一个共享数据库,存储于其中的数据或信息,具有“不可伪造”“全程留痕”“可以追溯”“公开透明”...

    2023-03-08
  • php开发工程师前景?

    php开发工程师前景 发展前景因各个企业不同而不一样,但是最终目标是一样的,就是开发出能挣钱的产品,所以就这点来说 PHP 也好,JAVA 也好,关键是否能给企业带来利益,利益越大...

    2023-09-23
  • 网页设计css是什么?

    CSS是什么 css指的是层叠样式表。css是一种用来表现HTML或XML等文件样式的计算机语言,是描述标记语言页面格式的标准。CSS使开发人员能够分离内容和可视元素,以实现更好的...

    2023-09-23
  • typecho悬浮音乐插件?

    我为什么选用typecho而不是wordpress作为博客 typecho 比较适合国内使用,毕竟是国人写的,而且有一点,对于国内的搜索引擎比较友好。 但是,动易的界面设计不符合个...

    2023-09-23

发表回复

登录后才能评论