golang 的 buffered channel 及 unbuffered channel
The channel is divided into two categories: unbuffered and buffered.
(1) Unbuffered channel
For unbuffered
channel, the sender will block on the channel until the receiver
receives the data from the channel, whilst the receiver will also block
on the channel until sender sends data into the channel. Check the
following example:
package main import (
"fmt"
"time"
) func main() {
ch := make(chan int) go func(ch chan int) {
fmt.Println("Func goroutine begins sending data")
ch <-
fmt.Println("Func goroutine ends sending data")
}(ch) fmt.Println("Main goroutine sleeps 2 seconds")
time.Sleep(time.Second * ) fmt.Println("Main goroutine begins receiving data")
d := <-ch
fmt.Println("Main goroutine received data:", d) time.Sleep(time.Second)
}
The running result likes this:
Main goroutine sleeps 2 seconds
Func goroutine begins sending data
Main goroutine begins receiving data
Main goroutine received data: 1
Func goroutine ends sending data
After the main goroutine is launched, it will sleep immediately("Main goroutine sleeps 2 seconds" is printed), and this will cause main goroutine relinquishes the CPU to the func goroutine("Func goroutine begins sending data" is printed). But since the main goroutine is sleeping and can't receive data from the channel, so ch <- 1 operation in func goroutine can't complete until d := <- ch in main goroutine is executed(The final 3 logs are printed).
(2) Buffered channel
Compared with unbuffered counterpart, the sender of buffered channel will block when there is no empty slot of the channel, while the receiver will block on the channel when it is empty. Modify the above example:
package main import (
"fmt"
"time"
) func main() {
ch := make(chan int, ) go func(ch chan int) {
for i := ; i <= ; i++ {
ch <- i
fmt.Println("Func goroutine sends data: ", i)
}
close(ch)
}(ch) fmt.Println("Main goroutine sleeps 2 seconds")
time.Sleep(time.Second * ) fmt.Println("Main goroutine begins receiving data")
for d := range ch {
fmt.Println("Main goroutine received data:", d)
}
}
The executing result is as follows:
Main goroutine sleeps 2 seconds
Func goroutine sends data: 1
Func goroutine sends data: 2
Main goroutine begins receiving data
Main goroutine received data: 1
Main goroutine received data: 2
Main goroutine received data: 3
Func goroutine sends data: 3
Func goroutine sends data: 4
Func goroutine sends data: 5
Main goroutine received data: 4
Main goroutine received data: 5
In this sample, since the channel has 2 slots, so the func goroutine will not block until it sends the third element.
P.S., "make(chan int, 0)" is equal to "make(chan int)", and it will create an unbuffered int channel too.
golang 的 buffered channel 及 unbuffered channel的更多相关文章
- [GO]无缓冲通道(unbuffered channel)
无缓冲通道(unbuffered channel)是指在接收前没有能力保存任何值的通道,在之前的例子中使用的都是无缓冲通道,需要注意的是,对于无缓冲通道而言,不管是往通道里写数据还是从通道里读数据,都 ...
- Golang的goroutine协程和channel通道
一:简介 因为并发程序要考虑很多的细节,以保证对共享变量的正确访问,使得并发编程在很多情况下变得很复杂.但是Go语言在开发并发时,是比较简洁的.它通过channel来传递数据.数据竞争这个问题在gol ...
- go语言之行--golang核武器goroutine调度原理、channel详解
一.goroutine简介 goroutine是go语言中最为NB的设计,也是其魅力所在,goroutine的本质是协程,是实现并行计算的核心.goroutine使用方式非常的简单,只需使用go关键字 ...
- 实时事件统计项目:优化flume:用file channel代替mem channel
背景:利用kafka+flume+morphline+solr做实时统计. solr从12月23号开始一直没有数据.查看日志发现,因为有一个同事加了一条格式错误的埋点数据,导致大量error. 据推断 ...
- netty源码解解析(4.0)-12 Channel NIO实现:channel初始化
创建一个channel实例,并把它register到eventLoopGroup中之后,这个channel然后处于inactive状态,仍然是不可用的.只有在bind或connect方法调用成功之后才 ...
- Netty Tutorial Part 1.5: On Channel Handlers and Channel Options [z]
Intro: After some feedback on Part 1, and being prompted by some stackoverflow questions, I want to ...
- Fibre Channel和Fiber Channel
Fibre Channel也就是"网状通道"的意思,简称FC. 由于Fiber和Fibre只有一字之差,所以产生了很多流传的误解. FC只代表Fibre Channel,而不是 ...
- golang channel 用法转的
一.Golang并发基础理论 Golang在并发设计方面参考了C.A.R Hoare的CSP,即Communicating Sequential Processes并发模型理论.但就像John Gra ...
- 深入学习golang(2)—channel
Channel 1. 概述 “网络,并发”是Go语言的两大feature.Go语言号称“互联网的C语言”,与使用传统的C语言相比,写一个Server所使用的代码更少,也更简单.写一个Server除了网 ...
随机推荐
- 在springBoot中配置web.xml中配置的servlet
第一种 web.xml (截取的需要转换的) 当拦截到 /socke t时执行该servlet <servlet> <servlet-name>websocket</se ...
- 终端IO(上)
一.综述 终端IO有两种不同的工作方式: 规范方式输入处理.在这种方式中,终端输入以行为单位进行处理.对于每个读要求,终端驱动程序最多返回一行. 非规范方式输入处理.输入字符不以行为单位进行装配 如果 ...
- Qt编写的开源帖子集合(懒人专用)
回顾自己学习Qt以来九年了,在这九年多时间里面,从本论坛学习不到不少的东西,今天特意整了一下自己开源过的资源的帖子,整理一起方便大家直接跳转下载,不统计不知道,一统计吓一跳,不知不觉开源了这么多代码, ...
- Error running app: Default Activity Not Found
最近在调试安装Android Widget程序时,碰到Error running app: Default ActivityNot Found. 因为简单的Widget程序,如果不和应用程序关联,就不 ...
- 10.22crm
2018-10-23 08:28:41 由于昨晚上断网,所以今天早上补更一下 越努力,越幸运!永远不要高估自己! crm老师就讲三四天,还有明后两天! 主要是讲一些基本使用,自定义配置陪一些东西! 主 ...
- solus 系统 - 安装编译工具
将会安装 gcc,make等工具 sudo eopkg install -c system.devel VirtualBox工具 https://solus-project.com/articles/ ...
- CMake error with move_base_msgs问题解决
错误 CMake Error at /opt/ros/groovy/share/catkin/cmake/catkinConfig.cmake: (find_package): Could not f ...
- 学习 rostopic
rostopic pub可以把数据发布到当前某个正在广播的话题上. rostopic pub [topic] [msg_type] [args] 示例 $ rostopic pub - /turtle ...
- [No0000EB]C# 数组(Array)
数组是一个存储相同类型元素的固定大小的顺序集合.数组是用来存储数据的集合,通常认为数组是一个同一类型变量的集合. 声明数组变量并不是声明 number0.number1.....number99 一个 ...
- jdbc实现分页,需要前端传当前页码
1.封装一个公共实体类用于返回:实体数据,当前页,总页数,总条数,每页多少条 public class PageInfo<T> { //一页显示的记录数 private int numPe ...