channel
我们先来看一下通道的解释:
channel是Go语言中的一个核心类型,可以把它看成管道。并发核心单元通过它就可以发送或者接收数据进行通讯,这在一定程度上又进一步降低了编程的难度。
channel是一个数据类型,主要用来解决go程的同步问题以及协程之间数据共享(数据传递)的问题。
goroutine运行在相同的地址空间,因此访问共享内存必须做好同步。goroutine 奉行通过通信来共享内存,而不是共享内存来通信。
引用类型 channel可用于多个 goroutine 通讯。其内部实现了同步,确保并发安全。

定义channel和使用
和map类似,channel也一个对应make创建的底层数据结构的引用。
当我们复制一个channel或用于函数参数传递时,我们只是拷贝了一个channel引用,因此调用者和被调用者将引用同一个channel对象。和其它的引用类型一样,channel的零值也是nil。
定义一个channel时,也需要定义发送到channel的值的类型。channel可以使用内置的make()函数来创建:
我们先来看一段代码

package main
import "fmt"
func main(){
ch:=make(chan int) //这里就是创建了一个channel,这是无缓冲管道注意
go func(){ //创建子go程
for i:=0;i<6;i++{
ch<-i //循环写入管道
fmt.Println("写入",i)
}
}()

for i:=0;i<6;i++{ //主go程
num:=<-ch //循环读出管道
fmt.Println("读出",num)
}
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
我们先看一下运行结果再来看代码:

我们在代码中 先创建了一个匿名函数的子go程,和main的主go程一起争夺cpu,但是我们在里面创建了一个管道,无缓冲管道有一个规则那就是必须读写同时操作才会有效果,如果只进行读或者只进行写那么会被阻塞,被暂时停顿等待另外一方的操作,在这里我们定义了一个容量为0的通道,这就是无缓冲通道,如下图

无缓冲通道就是这样,一次只能传输一个数据
总结一下就是无缓冲特性:
同一时刻,同时有 读、写两端把持 channel。
如果只有读端,没有写端,那么 “读端”阻塞。
如果只有写端,没有读端,那么 “写端”阻塞。
读channel: <- channel
写channel: channel <- 数据

有缓冲channel
如图所示:

. 在第 1 步,右侧的 goroutine 正在从通道接收一个值。
在第 2 步,右侧的这个 goroutine独立完成了接收值的动作,而左侧的 goroutine 正在发送一个新值到通道里。
在第 3 步,左侧的goroutine 还在向通道发送新值,而右侧的 goroutine 正在从通道接收另外一个值。这个步骤里的两个操作既不是同步的,也不会互相阻塞。
最后,在第 4 步,所有的发送和接收都完成,而通道里还有几个值,也有一些空间可以存更多的值。
有缓冲通道就是图中所示,一方可以写入很多数据,不用等对方的操作,而另外一方也可以直接拿出数据,不需要等对方写,但是注意一点(如果写入的一方把channel写满了,那么如果要继续写就要等对方取数据后才能继续写入,这也是一种阻塞,读出数据也是一样,如果里面没有数据则不能取,就要等对方写入),而有缓冲channel定义也比较简单

ch:=make(chan int,10)//chan int 只能写入读入int类型的数据,10代表容量为10.
1
这里用了自动推导类型来声明了一个有缓冲的channel
总结起来就是:
channel 中自带缓冲区。创建时可以指定缓冲区的大小。
w:直到缓冲区被填满后,写端才会阻塞。
r:缓冲区被读空,读端才会阻塞。
len:代表缓冲区中,剩余元素个数,
cap:代表缓冲区的容量。
在这里可以举个小小的例子来解释一下有缓冲channel和无缓冲channel
同步通信: 数据发送端,和数据接收端,必须同时在线。 —— 无缓冲channel
打电话。打电话只有等对方接收才会通,要不然只能阻塞

异步通信:数据发送端,发送完数据,立即返回。数据接收端有可能立即读取,也可能延迟处理。 —— 有缓冲channel 不用等对方接受,只需发送过去就行
发信息。短信。
是不是很形象呢
下一节将讲解一下channel常见的陷阱以及关闭channel

————————————————
版权声明:本文为CSDN博主「sgsgy5」的原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/sgsgy5/article/details/82054902

go之无缓冲channel(通道)和有缓冲channel(通道)的更多相关文章

  1. Halcon学习之三:有关图像通道的函数(R是三通道,B是1通道,G二通道),排列顺序BGR

    黑白摄像机会返回每个像素所对应的能量采用结果,这些结果组成了一幅单通道灰度值图像,而对于RGB彩色摄像机,它将返回每个像素所对应的三个采样结果,也就是一幅三通道图像.下面这些是与图像通道有关的函数: ...

  2. Caused by: com.rabbitmq.client.ShutdownSignalException: channel error; protocol method: #method<channel.close>(reply-code=406, reply-text=PRECONDITION_FAILED - inequivalent arg 'type' for exchange 'me

    在启动RabbitMQ消费端的时候报错:Caused by: com.rabbitmq.client.ShutdownSignalException: channel error; protocol ...

  3. STM32F10x_ADC三通道DMA连续转换(3通道、软件单次触发)

    Ⅰ.概述 上一篇文章讲述的内容是:三通道逐次转换(单次.单通道软件触发),也就是说3条通道要三次软件触发才能完成转换,而且是通过软件读取转换数值. 本文讲述三通道DMA连续转换(3通道.软件单次触发) ...

  4. 使用opencv为没有透明通道的图像加入透明通道

    在图像处理中,我们经常需要处理带透明通道的图片,比如为图片或视频添加水印,为图片或视频添加字幕.贴图等.然而,我们的素材图片未必总是带有透明通道.比如,素材的背景本该透明的地方,却是黑色和白色.有时, ...

  5. 标准I/O缓冲:全缓冲、行缓冲、无缓冲

    说明:我仅仅对网络资源进行了整合,方便学习-.- 基于流的操作终于会调用read或者write函数进行I/O操作.为了使程序的执行效率最高,流对象一般会提供缓冲区,以降低调用系统I/O库函数的次数. ...

  6. EasyNVR摄像机网页Chrome无插件视频播放功能二次开发之通道配置文件上传下载示例代码

    背景需求 熟悉EasyNVR产品的朋友们都知道,产品设计初期根据整个直播流程层级,我们将EasyNVR无插件直播系统划分为:硬件层.能力层.应用层,连接硬件与应用之间的桥梁,同时屏蔽各种厂家硬件的不同 ...

  7. cell下载图片的思路 --无沙盒(内存)缓冲

    // // ViewController.m // 06-表格图片下载 // // Created by jerry on 15/9/7. // Copyright (c) 2015年 jerry. ...

  8. EasyNVR无插件直播服务器软件使用详情功能-通道配置Excel

    背景需求 使用EasyNVR的用户都有知道,由于EasyNVR是将设备与EasyNVR的通道进行绑定的,因此EasyNVR是通过手动的通道配置来进行设备接入的,这样可以做到将设备的和通道对应的接入.但 ...

  9. [bigdata] flume file channel CPU消耗比 memory channel高的原因

    https://www.quora.com/Why-does-flume-take-more-resource-CPU-when-file-channel-is-used-compared-to-wh ...

随机推荐

  1. Photoshop从入门到精通所有视频教程(43G)以及素材资料免费拿

    包含了Photoshop从入门到精通所有需要了解的视频教程资料,并且包含了大量的P图素材. 资料获取方式,关注公总号RaoRao1994,查看往期精彩-所有文章,即可获取资源下载链接 更多资源获取,请 ...

  2. 经典i++和++i问题(附带运算符优先级问题)

    转自 https://blog.csdn.net/mustard1020/article/details/79617865 1.i++和++i的区别     (1)i++简单来说就是先用i的值来参加表 ...

  3. Vivotek 摄像头远程栈溢出漏洞分析及利用

    Vivotek 摄像头远程栈溢出漏洞分析及利用 近日,Vivotek 旗下多款摄像头被曝出远程未授权栈溢出漏洞,攻击者发送特定数据可导致摄像头进程崩溃. 漏洞作者@bashis 放出了可造成摄像头 C ...

  4. AIX文件系统/var空间100%的问题

    一.问题说明/var/spool/mqueue目录下出现了多个df打头的文件,导致/var空间最终100% EBANK_P570_MAIN/var/spool/mqueue#ls -l total 8 ...

  5. KMP算法详解&&P3375 【模板】KMP字符串匹配题解

    KMP算法详解: KMP算法是一种改进的字符串匹配算法,由D.E.Knuth,J.H.Morris和V.R.Pratt(雾)提出的. 对于字符串匹配问题(such as 问你在abababb中有多少个 ...

  6. mysqldump恢复

    mysqldump的恢复操作比较简单,因为备份的文件就是导出的SQL语句,一般只需要执行这个文件就可以了,可以通过以下的方法. 方法一 [root@zstedu andyxi3306]# mysql ...

  7. HTML 获取class里的多个值 和 dataset的使用

    属性:classList var x = event.target; console.log(x); console.log(x.classList); 可以发现 获取了全部的class里的值 获取单 ...

  8. BZOJ 1984: 月下“毛景树” (树链剖分+线段树)

    注意赋值和加法的标记下传优先级.具体看代码. CODE #include <vector> #include <queue> #include <cstdio> # ...

  9. FZU-1901-Period 2(KMP)

    链接: https://vjudge.net/problem/FZU-1901 题意: For each prefix with length P of a given string S,if S[i ...

  10. 2 APIView与序列化组件

    1.入门 1.1 参考blog 官方文档:http://www.django-rest-framework.org/tutorial/quickstart/#quickstart yuan的Blog: ...