1、管道分类

  • 读写管道
  • 只读管道
  • 只写管道
  • 缓冲通道 :创建时指定大小(如果不指定默认为非缓冲通道)

2、正确使用管道

  1. 管道关闭后自能读,不能写

  2. 写入管道不能超过管道的容量cap,满容量还写则会阻塞

  3. 管道为空时,如果没有关闭,则继续读取会阻塞当前线程,直到有东西写入管道

  4. m,ok:=<-intChan  //ok用来检测产是否已经关闭 false代表关闭了,关闭了m就是默认值

    一般如下操作才可以判断读取是否完毕,如果写进程没有关闭管道则说明还有东西要写

    v,ok:=<-intChan
    if !ok{
    fmt.Println("读取完毕")
    break
    }

3、管道遍历与访问

  • for-range访问
  • select访问(常用)

for-range

//gor-range  如果管道没有数据同时还没有关闭  则会一直阻塞等待
go func() {
for i:=range c{ //注意这里没有ok判断是否关闭了 只有一个返回值
fmt.Println(i)
}
}()

下面这种情况for-range会阻塞,1秒后打印1,和 “关闭了”,如果没写同时又没有关闭,那么则会一直阻塞

	ch := make(chan int)
go func() {
time.Sleep(time.Second)
//close(ch)
ch<-1
}()
go func() {
for i:=range ch{
log.Println(i)
}
log.Println("关闭了")
}()
time.Sleep(time.Hour)

下面的这种情况,for-range在一秒后会结束 ,同时打印“关闭了”

	ch := make(chan int)
go func() {
time.Sleep(time.Second)
close(ch)
//ch<-1
}()
go func() {
for i:=range ch{
log.Println(i)
}
log.Println("关闭了")
}()
time.Sleep(time.Hour)

select

select会随机选择case里面没有阻塞的管道进行读取或写入,如果都阻塞则执行default语句,一般select都会伴随一个default语句

	c:=make(chan string,2)
send:= func(v string) {
select {
case c<-v:log.Println("输入",v)
default:log.Println("缓冲区已经满")
}
} receive:= func() string {
select {
case v:=<-c:return v
default:
log.Println("缓冲区空")
return ""
}
} send("h1")
send("h2")
send("h3") //输入失败 log.Println(receive())
log.Println(receive())
log.Println(receive()) //取失败

当管道关闭时,select也会执行成功,如下打印了一秒‘等' 之后就会结束,这里没有往管道写东西,所以结束时打印的是默认值0

	ch := make(chan int)
//go func() {
// ch <- 1
//}()
go func() {
time.Sleep(time.Second)
close(ch) }()
go func() {
for {
time.Sleep(time.Microsecond*500)
select {
case v := <-ch:
log.Println(v)
return
default:
log.Println("等")
}
}
}()
time.Sleep(time.Hour)

4、阻塞情况

1、没有关闭,同时管道元素为0,读进程阻塞

2、没有关闭,同时管道元素已经满,则写进程阻塞,无缓冲管道的话则会阻塞在写,直到有人读

3、关闭管道,读光了还读,则读取出来的是对应类型管道的默认空值,在一个关闭通道进行写操作会报错

	ch:=make(chan int,1)
ch<-1
close(ch) log.Println(<-ch) //1
log.Println(<-ch) //0
log.Println(<-ch)//0
a,ok:=<-ch
log.Println(a,ok)//0 false
  1. 关闭管道,还写,则报错

  2. 无缓冲=堵塞,缓冲=非堵塞 无缓冲是同步,有缓冲是异步

像下面这个无缓冲管道,没人读则一直阻塞,只会打印A1,有一个管道读走了才会继续执行写操作,就比如快递员来发快递,只会等你拿走快递才会离开,否则一直在等你来拿

	ch := make(chan int)
go func() {
for{
log.Println("A1")
time.Sleep(time.Second)
//close(ch)
ch<-1
log.Println("A2")
} }()

那如果我把cap设置成1呢?

	ch := make(chan int,1)
go func() {
for{
log.Println("A1")
time.Sleep(time.Second)
//close(ch)
ch<-1
log.Println("A2")
} }()

打印如下,可以写一个

2020/03/21 20:02:59 A1
2020/03/21 20:03:00 A2
2020/03/21 20:03:00 A1

其他关于通道的使用可以看这两篇博客

go通道的常见使用场景.

go通道的优雅关闭.

channel的基本使用的更多相关文章

  1. Golang, 以17个简短代码片段,切底弄懂 channel 基础

    (原创出处为本博客:http://www.cnblogs.com/linguanh/) 前序: 因为打算自己搞个基于Golang的IM服务器,所以复习了下之前一直没怎么使用的协程.管道等高并发编程知识 ...

  2. TODO:Go语言goroutine和channel使用

    TODO:Go语言goroutine和channel使用 goroutine是Go语言中的轻量级线程实现,由Go语言运行时(runtime)管理.使用的时候在函数前面加"go"这个 ...

  3. GO语言之channel

    前言: 初识go语言不到半年,我是一次偶然的机会认识了golang这门语言,看到他简洁的语法风格和强大的语言特性,瞬间有了学习他的兴趣.我是很看好go这样的语言的,一方面因为他有谷歌主推,另一方面他确 ...

  4. Critical: Update Your Windows Secure Channel (cve-2014-6321,MS14-066)

    前言:风雨欲来山满楼,下半年开始各种凶猛的漏洞层出不穷,天下已经不太平,互联网已经进入一个新的台阶 0x01 cve-2014-6321 11月的补丁月,微软请windows的用户吃了顿大餐,发布了1 ...

  5. JAVA NIO Channel

    Basic:   多数通道都是链接到开发的文件描述符的.Channel类提供维持平台独立性的抽象过程.   通道是一种途径,访问和操作操作系统,缓冲区是数据操作点: Channel类继承结构图: 通过 ...

  6. channel Golang

    Golang, 以17个简短代码片段,切底弄懂 channel 基础 (原创出处为本博客:http://www.cnblogs.com/linguanh/) 前序: 因为打算自己搞个基于Golang的 ...

  7. go channel

    channel 是go语言中不同goroutine之间通信一种方法 //定义一个channel c := make(chan bool) //向channel中写入 c <- true //读取 ...

  8. [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 ...

  9. 图解Netty之Pipeline、channel、Context之间的数据流向。

    声明:本文为原创博文,禁止转载.       以下所绘制图形均基于Netty4.0.28版本. 一.connect(outbound类型事件)  当用户调用channel的connect时,会发起一个 ...

  10. go:channel(未完)

    注:1)以下的所有讨论建立在包含整形元素的通道类型之上,即 chan int 2)对于“<-”我的理解是,它可能是一个操作符(接收操作符),也  可能是类型的一部分(如“chan<- in ...

随机推荐

  1. Win32下双缓冲绘图技术

    一:双缓冲原理 为了解决窗口刷新频率过快所带来的闪烁问题,利用双缓冲技术进行绘图.所谓双缓冲技术,就是将资源加载到内存,然后复制内存数据到设备DC(这个比较快),避免了直接在设备DC上绘图(这个比较慢 ...

  2. Nginx笔记总结十三:sub_filter内容替换

    Nginx变异安装加上参数 --with-http_sub_module 配置文件: location ~* ^/portalproxy/([-]*)/portal(.*)$ { #sub_filte ...

  3. python多重逻辑排序

    python有自带的排序sorted函数,而且用reverse =True or False,来控制降序还是升序.但是如果有多个条件需要排序应该如何办呢? L = [(12, 12), (34, 13 ...

  4. idea如何使用git

    1.安装好git(我下载的2.23.0版本百度网盘分享)  提取码  7ie1 2.配置git环境变量  Path   路径是你安装的git 目录下的bin目录   安装好后窗口命令输入git 可以测 ...

  5. sycPHPCMS v1.6 cookie sqlinjection

    ./user/index.php include "../include/conn.php"; include "../include/function.php" ...

  6. 想清楚再入!VR硬件创业能“要你命”

    每一次跨时代新产品的出现,总会让科技行业疯狂一阵儿,十年前是智能手机,今天自然是VR.自2015年开始,VR火的越来越让人欣喜,让人兴奋,更让人越来越看不清,越来越害怕.数不清的大小品牌义无反顾的杀入 ...

  7. 用RecyclerView做一个小清新的Gallery效果 - Ryan Lee的博客

    一.简介 RecyclerView现在已经是越来越强大,且不说已经被大家用到滚瓜烂熟的代替ListView的基础功能,现在RecyclerView还可以取代ViewPager实现Banner效果,当然 ...

  8. RTL8812AU双频无线网卡在ubuntu19和20上的驱动安装

    旧爱已去 疫情在家,突然邻居敲门说,我这网上不了,帮下忙呗兄弟:兄弟都叫了,哥就冒回险,口罩扎起,一顿xxxx,原来是路由器没插到wlan口,看他拉网线可怜,就把我台式机上无线网卡送给他了,这就是又送 ...

  9. 基于 HTML5 Canvas 的 3D 热力云图效果

    前言 数据蕴藏价值,但数据的价值需要用 IT 技术去发现.探索,可视化可以帮助人更好的去分析数据,信息的质量很大程度上依赖于其呈现方式.在数据分析上,热力图无疑是一种很好的方式.在很多行业中都有着广泛 ...

  10. percona-toolkit 之 【pt-query-digest】使用

    背景 关于pt-query-digest的使用场景和方法在percona-toolkit 之 [pt-query-digest]介绍文章里已经做了详细说明,现在开始介绍下如何使用,以及常用的命令. 使 ...