Go语言中的有缓冲channel和无缓冲channel区别
Go语言中的有缓冲channel和无缓冲channel区别
结论
ch1:=make(chan int)// 无缓冲
ch2:=make(chan int,1)// 有缓冲
无缓冲: 当向ch1中存值后需要其他协程取值,否则一直阻塞
有缓冲: 不会阻塞,因为缓冲大小是1,只有当放第二个值的时候,第一个还没被人拿走,才会阻塞。
测试程序
测试1,声明无缓冲channel
func Test_1(t *testing.T) {
// 无缓冲
ch := make(chan int)
// fatal error: all goroutines are asleep - deadlock! 协程阻塞,需要另一个协程取走channel中的值
ch <- 1
}
运行结果:
=== RUN Test_1
fatal error: all goroutines are asleep - deadlock!
goroutine 1 [chan receive]:
testing.(*T).Run(0xc0000c0100, 0x55bb8e, 0x6, 0x566b20, 0x47e55d)
D:/Go/src/testing/testing.go:961 +0x37e
testing.runTests.func1(0xc0000c0000)
D:/Go/src/testing/testing.go:1202 +0x7f
testing.tRunner(0xc0000c0000, 0xc00008fdc0)
D:/Go/src/testing/testing.go:909 +0xd0
testing.runTests(0xc000060460, 0x654300, 0x4, 0x4, 0x0)
D:/Go/src/testing/testing.go:1200 +0x2ae
testing.(*M).Run(0xc0000b6000, 0x0)
D:/Go/src/testing/testing.go:1117 +0x17d
main.main()
_testmain.go:50 +0x13c
goroutine 19 [chan send]:
test/review.Test_1(0xc0000c0100)
E:/Go/src/test/review/main_test.go:64 +0x57
testing.tRunner(0xc0000c0100, 0x566b20)
D:/Go/src/testing/testing.go:909 +0xd0
created by testing.(*T).Run
D:/Go/src/testing/testing.go:960 +0x357
Process finished with exit code 1
测试2,开启协程取值
func Test_2(t *testing.T) {
// 无缓冲
ch := make(chan int)
go func() {
// 睡眠1秒,等待主协程在channel写入值
time.Sleep(time.Second * 1)
fmt.Println("开始取值。。。")
<-ch
}()
fmt.Println("开始存值。。。")
ch <- 1
time.Sleep(time.Second*5)
fmt.Println("结束。。。")
}
运行结果:
=== RUN Test_2
开始存值。。。
开始取值。。。
结束。。。
--- PASS: Test_2 (6.00s)
PASS
Process finished with exit code 0
测试3,声明有缓冲channel
func Test_3(t *testing.T) {
// 有缓冲
ch1 := make(chan int, 1)
// 缓冲大小为1 即是当channel中有一个值时不会被阻塞,当再塞入一个时前一个没被其他协程取走才会阻塞
ch1 <- 2
// 此时主协程也可取出值
fmt.Println(<-ch1)
}
运行结果:
=== RUN Test_3
2
--- PASS: Test_3 (0.00s)
PASS
Process finished with exit code 0
测试4,存入超过缓冲数量的值
func Test_4(t *testing.T) {
// 有缓冲
ch1 := make(chan int, 1)
// 缓冲大小为1 即是当channel中有一个值时不会被阻塞,当再塞入一个时前一个没被其他携程取走才会阻塞
ch1 <- 1
// fatal error: all goroutines are asleep - deadlock!
ch1 <- 2
}
测试结果:
=== RUN Test_4
fatal error: all goroutines are asleep - deadlock!
goroutine 1 [chan receive]:
testing.(*T).Run(0xc0000a8100, 0x55bba0, 0x6, 0x566b40, 0x47e501)
D:/Go/src/testing/testing.go:961 +0x37e
testing.runTests.func1(0xc0000a8000)
D:/Go/src/testing/testing.go:1202 +0x7f
testing.tRunner(0xc0000a8000, 0xc000081dc0)
D:/Go/src/testing/testing.go:909 +0xd0
testing.runTests(0xc0000044c0, 0x654300, 0x4, 0x4, 0x0)
D:/Go/src/testing/testing.go:1200 +0x2ae
testing.(*M).Run(0xc00009e000, 0x0)
D:/Go/src/testing/testing.go:1117 +0x17d
main.main()
_testmain.go:50 +0x13c
goroutine 6 [chan send]:
test/review.Test_4(0xc0000a8100)
E:/Go/src/test/review/main_test.go:97 +0x76
testing.tRunner(0xc0000a8100, 0x566b40)
D:/Go/src/testing/testing.go:909 +0xd0
created by testing.(*T).Run
D:/Go/src/testing/testing.go:960 +0x357
Process finished with exit code 1
Go语言中的有缓冲channel和无缓冲channel区别的更多相关文章
- Golang并发编程有缓冲通道和无缓冲通道(channel)
无缓冲通道 是指在接收前没有能力保存任何值得通道.这种类型的通道要求发送goroutine和接收goroutine同时准备好,才能完成发送和接收操作.如果两个goroutine没有同时准备好,通道会导 ...
- golang的缓冲channel和无缓冲channel的区别
话说golang的channel同步的定义真是让人无力吐槽,码农的用户体验就这么难搞么,超耐磨阿,无缓冲和缓冲居然有这么大区别....靠 转载一段网上的资料 --------------------- ...
- 论C语言中二级指针和二维数组之间的区别
刚开始学习C语言的时候,觉得一个数组可以定义一个一级指针去访问,想当然的就觉得可以定义一个二级指针去访问二维数组.很显然这是错误的. 我们来看看C语言的数组在内存中的存储方式. 实际上C语言中的数组, ...
- C语言中整形数组、字符数组、字符串的区别
一. 第一 整型数组的存放,数组最后是不加'\0'的,字符串会自动加上,因此存放字符的时候数组的大小要比实际字符的多一个 第二 整型数组 每一个单元是4个字节的,字符串是一个一个字符存放的,每个字符占 ...
- C语言中指针*p[N], (*P)[N],及**p的区别
在C语言编程中指针经常困扰着我们,但是若能灵活运用指针的话,将会使得我们编程变得更加轻松与高效.这里讲下*p[N], (*P)[N],及**p的区别,这也是之前经常困扰我的地方. 这三者的定义分别为: ...
- C语言中访问结构体成员时用‘.’和‘->’的区别
举个例子,定义了一个叫Student,别名为stu的结构类型,我们声明了一个结构体变量叫stu1,声明了一个结构体指针为stuP. typedef struct Student { char name ...
- C语言中各数据类型(eg.int和float的区别)
- go之无缓冲channel(通道)和有缓冲channel(通道)
channel我们先来看一下通道的解释:channel是Go语言中的一个核心类型,可以把它看成管道.并发核心单元通过它就可以发送或者接收数据进行通讯,这在一定程度上又进一步降低了编程的难度.chann ...
- Go语言中的并发编程
并发是编程里面一个非常重要的概念,Go语言在语言层面天生支持并发,这也是Go语言流行的一个很重要的原因. Go语言中的并发编程 并发与并行 并发:同一时间段内执行多个任务(你在用微信和两个女朋友聊天) ...
随机推荐
- mouseenter mouseleave鼠标悬浮离开事件
- Deepin深度应用商店和系统更新不正常的解决方法
Deepin深度应用商店和系统更新不正常的解决方法 2020-02-04 10:25:09作者:i8520稿源:深度站 如果你的Deepin深度应用商店和系统更新不正常,可采用以下方法来解决问题. 解 ...
- 016.Python闭包函数以及locals和globals
一 闭包函数 内函数使用了外函数的局部变量,并且外函数把内函数返回出来的过程叫做闭包,这个内函数叫做闭包函数 1.1 闭包函数语法 def outer(): a = 5 def inner(): pr ...
- 使用Mybatis插件 PageHelper 模拟百度分页(Day_20)
生活中,要学会沉淀生命,沉淀心情,沉淀自己 模拟百度分页最终实现效果如图: 本篇博客运行环境 JDK8 + IntelliJ IDEA 2018.3 + Tomcat 8.5.31 准备好了我们就开始 ...
- 『动善时』JMeter基础 — 26、使用txt文件实现JMeter参数化
目录 1.测试计划中的元件 2.数据文件内容 3.线程组元件内容 4.HTTP信息头管理器组件内容 5.CSV数据文件设置组件内容 6.HTTP请求组件内容 7.脚本运行结果 之前我们都是使用.csv ...
- 在pycharm进行单元测试(unittest python)
在Edit Configuration中添加Python test 选中相应的脚本或者文件夹 # coding:utf-8 import unittest import requests from c ...
- Django(43)restful接口规范
restful接口规范 什么是接口规范?接口规范就是为了采用不同的后台语言,也能使用同样的接口获取到同样的数据.如何写接口:接口规范是规范化书写接口的,写接口要写url.响应数据 注:如果将 ...
- 微服务架构(Microservices) ——Martin Flower
不知不觉到达了Sring Boot的学习中了,在学习之前,了解微服务架构是很有必要的,对于自己提升今后面试的软实力有很大帮助,在此写下. 让我们接下来看下Martin Flower 如何解释微服务架构 ...
- mybatis运行出现org.apache.ibatis.binding.BindingException
今天学习mybatis的第一天,发现用junit测试报出了次异常:org.apache.ibatis.binding.BindingException: Type interface cn.dzp.d ...
- python实现布隆过滤器及原理解析
python实现布隆过滤器及原理解析 布隆过滤器( BloomFilter )是一种数据结构,比较巧妙的概率型数据结构(probabilistic data structure),特点是高效地 ...