Golang协程与通道整理

摘要:
常见问题包括创建、关闭或删除、阻塞、超时、优先级等,golang中也不例外。若该信道为nil,则range表达式将永远阻塞经过试验,range会阻塞,并且可以通过关闭channel来解除阻塞。")}Golang的并发编程还有其他细节,但以上是最主要脉络。
协程goroutine
不由OS调度,而是用户层自行释放CPU,从而在执行体之间切换。Go在底层进行协助实现
涉及系统调用的地方由Go标准库协助释放CPU
总之,不通过OS进行切换,自行切换,系统运行开支大大降低
通道channel
并发编程的关键在于执行体之间的通信,go通过通过channel进行通信
channel可以认为类似其他OS体系中的消息队列,只不过在go中原生支持,因而易用
消息队列有哪些值得关注的地方?常见问题包括创建、关闭或删除、阻塞、超时、优先级等,golang中也不例外。罗列如下:
可否探测队列是满或空?或者说是否可以不阻塞地尝试读写?
读阻塞和写阻塞时关闭会怎样?
关闭后未读取的消息会被抛弃?
往关闭的channel发送数据或读取数据会怎样?
怎样探测channel的关闭?
两个地方读或写阻塞同一个channel,有没有优先级?
是否可以设定阻塞的超时时间?
阻塞时怎样可以被弹出来?比如某些信号?
事实上,知道存在这些问题并进行分门别类是重要的,但知道这些问题的答案却不紧要,因为一般不会太过古怪,使用时临时试验一下即可。
已知的部分答案:
好像不能不阻塞地尝试读写
关闭会导致退出阻塞(似乎是一个不错的特性)
可以探测关闭
channel本身不能设定超时
了解这些似乎已经足够。
与众不同的地方值得我们重点留意,包括:
除基本读写方式外,还有哪些特别的读写方式?在阻塞、关闭、超时方面又有什么不同?发现了select、range两个关键字
推荐的多通道读
推荐的同步方法
推荐的超时方法
select
select可以实现无阻塞的多通道尝试读写,以及阻塞超时
varc, c1, c2, c3chanint
vari1, i2int
select{
casei1 = <-c1://如果能走通任何case则随机走一个
print("received ", i1," from c1 ")
casec2 <- i2:
print("sent ", i2," to c2 ")
casei3, ok := (<-c3):
ifok {
print("received ", i3," from c3 ")
}else{
print("c3 is closed ")
}
default:// 如果case都阻塞,则走default,如果无default,则阻塞在case
// default中可以不读写任何通道,那么只要default提供不阻塞的出路,就相当于实现了对case的无阻塞尝试读写
print("no communication ")
}
实现阻塞超时的方法是,只要不给default出路,而在case中实现一个超时
timeout :=make(chanbool, 1)
gofunc() {
time.Sleep(1e9)// 这是等待1秒钟
timeout <-true
}()
// 用timeout这个通道作为阻塞超时的出路
select{
case<-ch:
// 处理从ch中读到的数据
case<-timeout:
// 如果case都阻塞了,那么1秒钟后会从这里找到出路
}
range
range可以在for循环中读取channel
Go文档的翻译文是:对于信道,其迭代值产生为在该信道上发送的连续值,直到该信道被关闭。若该信道为 nil,则range表达式将永远阻塞
经过试验,range会阻塞,并且可以通过关闭channel来解除阻塞。
packagemain
import(
"fmt"
)
funcmain() {
ch :=make(chanint)
gofunc() {
fori := 0; i < 10; i++ {
ch <- i
}
}()
forw :=rangech {
fmt.Println("fmt print", w)
ifw > 5 {
//break // 在这里break循环也可以
close(ch)
}
}
fmt.Println("after range or close ch!")
}
Golang的并发编程还有其他细节,但以上是最主要脉络。

免责声明:文章转载自《Golang协程与通道整理》仅用于学习参考。如对内容有疑问,请及时联系本站处理。

上篇基于Siverlight 3.0的超炫图表工具Visifire 最后一个免费版本,你还等什么?转载(正则表达式的分类) 规格严格下篇

宿迁高防,2C2G15M,22元/月;香港BGP,2C5G5M,25元/月 雨云优惠码:MjYwNzM=

相关文章

游标(cursor)--显式游标&amp;amp;隐式游标、游标四个属性、循环遍历

https://blog.csdn.net/qq_36743482/article/details/79354036 1.1 cursor是什么cursor是光标,游标的意思。比如我们的鼠标的光标就是cursor。那么在数据库中cursor是什么呢?当运行DML(select,update,insert,delete)语句时,ORACLE会在内存中为其分配...

python网络编程

一:进程间的通信 1.本地进程间的通信   消息传递(管道,FIFO,消息队列)   同步(互斥量,条件变量,读写锁,文件和写记录锁,信号量)   共享内存(匿名的和具名的) 远程过程调用    2.网络进程间的通信 网络上的进程对得唯一区分,这样才能进行网络间的通信,比如QQ,微信聊天等等。而可以唯一区分的是进程的ip地址(互联网协议地址),协议,...

MySQL排序原理与MySQL5.6案例分析【转】

本文来自:http://www.cnblogs.com/cchust/p/5304594.html,其中对于自己觉得是重点的加了标记,方便自己查阅。更多详细的说明可以看沃趣科技的文章说明。 前言      排序是数据库中的一个基本功能,MySQL也不例外。用户通过Order by语句即能达到将指定的结果集排序的目的,其实不仅仅是Order by语句,Gr...

netty5客户端监测服务端断连后重连

  服务端挂了或者主动拒绝客户端的连接后,客户端不死心,每15秒重连试试,3次都不行就算了。修改下之前的客户端引导类(NettyClient,参见netty5心跳与业务消息分发实例),新增两个成员变量,在connect连接方法里的finally加入重连操作: private ScheduledExecutorService executorServ...

数据绑定流程分析

1.    数据绑定流程原理★ ①   Spring MVC 主框架将 ServletRequest  对象及目标方法的入参实例传递给 WebDataBinderFactory 实例,以创建 DataBinder 实例对象 ②   DataBinder 调用装配在 Spring MVC 上下文中的 ConversionService 组件进行数据类型转换、...

CentOS7 编译安装golang和rpm安装golang

编译安装 1、下载golang二进制安装包: https://storage.googleapis.com/golang/go1.9.linux-amd64.tar.gz 2、解压安装包到指定目录,此处以解压到/usr/local目录下为例: 1 tar -C /usr/local -xzf ../packages/go1.8.linux-amd64.ta...