golang篇-2021秋招准备

1、GPM

  • G(Goroutine) :我们所说的协程,为用户级的轻量级线程,每个Goroutine对象中的sched保存着其上下文信息

  • M(Machine) :对内核级线程的封装,数量对应真实的CPU数(真正干活的对象)

  • P(Processor)

    • 即为G和M的调度对象,用来调度G和M之间的关联关系,其数量可通过GOMAXPROCS()来设置,默认为核心数
    • P为M的执行提供了上下文,保存了M执行G的一些基本信息,保存了等待执行的G队列……
      M只有绑定P才可以去执行G

每个Processor对象都拥有一个LRQ(Local Run Queue),未分配的Goroutine对象保存在GRQ(Global Run Queue )中,等待分配给某一个P的LRQ中,每个LRQ里面包含若干个用户创建的Goroutine对象,同时Processor作为桥梁对Machine和Goroutine进行了解耦,也就是说Goroutine如果想要使用Machine需要绑定一个Processor才行,上图中共有两个M和两个P也就是说我们可以同时并行处理两个goroutine

title

title

2、Channel

无缓冲channel与有缓冲channel
  • 无缓冲的是默认,同步

  • 缓冲是1的缓冲式,异步
    其实是彻底错误的,无缓冲的与有缓冲channel有着重大差别

比如

1
2
3
c1:=make(chan int) 无缓冲
c2:=make(chan int,1) 有缓冲
c1<- 1

无缓冲的通道保证进行发送和接收的 goroutine 会在同一时间进行数据交换;有缓冲的通道没有这种保证

无缓冲的 不仅仅是向c1通道放 1 而是 一直要有别的协程 <-c1 接手了 这个参数,那么c1<-1才会继续下去,要不然就一直阻塞着
c2<-1 则不会阻塞,因为缓冲大小是1 (其实是缓冲大小为0)只有当放第二个值的时候 第一个还没被人拿走,这时候才会阻塞

通道关闭:关闭通道的代码非常重要。当通道关闭后,goroutine 依旧可以从通道接收数据,但是不能再向通道里发送数据。能够从已经关闭的通道接收数据这一点非常重要,因为这允许通道关闭后依旧能取出其中缓冲的全部值,而不会有数据丢失。从一个已经关闭且没有数据的通道里获取数据,总会立刻返回,并返回一个通道类型的零值。如果在获取通道时还加入了可选的标志,就能得到通道的状态信息。


golang篇-2021秋招准备
https://zhangfuli.github.io/2021/08/02/2021秋招准备-golang篇/
作者
张富利
发布于
2021年8月2日
许可协议