Go并发、协程、通道 9

简单介绍:并发、协程、通道
这里记录的是我个人不太熟练的语法和知识
详细内容移步:李文周的博客(非常详细)
#并发
并行:多个单核“CPU”或多个“CPU核心”在同时运行不同的任务,称不同任务的并行。

并发:一个单核“CPU”或一个“CPU核心”在多个任务间不断快速切换运行,称多个任务在并发。

因为各种资源的调度都需要时间,在高并发的场景下,CPU利用率会相对高一些。

#协程
开启一个协程非常简单:

go func(){
}

这就开启了一个啥都没干的匿名函数。
一般使用协程都是为了进行高并发,
多以会结合for循环使用。

for i:= 0 ; i<?;i++{
go ???(){	
  }
}

协程与线程的比较
一个协程初始状态下大概只有2kb左右,也可以自动扩容到1Gb(一般不会这样用吧),这是动态扩容的效果;
协程是“用户级线程”,即使程序有数以千计的 Go 协程,也可能只有一个线程;
协程通过通道进行数据交换,可以防止多个协程访问共享数据发生竞争。


https://blog.csdn.net/NikoKVCS/article/details/90295887
特性:
该协程主动要求切换给其他协程
该协程执行时遇到堵塞,比如在等待 IO 读数据,或者读channel时陷入等待,这样就会被CPU强行切换到其他协程
https://www.php.cn/be/go/439681.html
每个线程都有一个id,在线程创建的时候就会被返回,所以我们可以通过线程的id来操纵线程。但是在golang中没有这个概念,因此我们在编码之初就要考虑协程的创建和释放问题。
线程涉及模式切换(从用户态切换到内核态)、16个寄存器、PC、SP…等寄存器的刷新等。
因为协程在用户态由协程调度器完成,不需要陷入内核,这代价就小了。
#通道
https://www.liwenzhou.com/posts/Go/14_concurrence/#autoid-1-3-3
channel类型类似一种队列,遵循先进先出原则。
关于关闭通道需要注意的事情是,只有在通知接收方goroutine所有的数据都发送完毕的时候才需要关闭通道。通道是可以被垃圾回收机制回收的,它和关闭文件是不一样的,在结束操作之后关闭文件是必须要做的,但关闭通道不是必须的。
关闭通道

close(ch)

关闭后的通道有以下特点:

对一个关闭的通道再发送值就会导致panic。
对一个关闭的通道进行接收会一直获取值直到通道为空。
对一个关闭的并且没有值的通道执行接收操作会得到对应类型的零值。
关闭一个已经关闭的通道会导致panic。

var ch = make(chan<- int)  //单向
ch := make(chan int, 1)    //带缓冲
ch <- 10
//····················
func main() {
	ch := make(chan int, 1)
	for i := 0; i < 10; i++ {
		select { //select多路复用
		case x := <-ch:
			fmt.Println(x)
		case ch <- i:
		}
	}
}

select多路复用

  1. 可处理一个或多个channel的发送/接收操作。
  2. 如果多个case同时满足,select会随机选择一个。
  3. 对于没有case的select{}会一直等待,可用于阻塞main函数。


https://www.cnblogs.com/chenqionghe/p/13919427.html(非常详细)

var a sync.WaitGroup
a.Add(1)
a.Done()
a.Wait()
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值