golang select default continue_Go并发(四):select篇
转载于公众号:灰子学技术
原文链接:https://mp.weixin.qq.com/s/nJRVbhRQCgWHR1eHSfBpFA
一、前言介绍:
对于Go语言并发通讯,是使用的协程goroutine,而协程之间的通讯采用的是channel。但是channel不管是有缓存的,还是无缓存的都会有阻塞的情况出现,只不过无缓存的阻塞会更加频繁。而协程长时间阻塞了之后,Go语言本身又没有提供这种超时的解决机制,所以开发者需要自己考虑实现这种超时机制。这种超时机制在Go语言中则是使用select来解决的。
相关的背景知识:
1.Go语言并发篇(一):之go语句篇:https://mp.weixin.qq.com/s/FD-MP9r5sEn1QYRAYZE_4g
2.Go语言之goroutine的调度原理: https://mp.weixin.qq.com/s/hTgIyJN7p-wrDfLj1bP1wQ
3.Go并发之channel篇:https://mp.weixin.qq.com/s/PIb-gGBootc6581pHhi5ew
二、Select内容介绍
我们先来看几个问题, select是什么?它都有那些特性?
语法定义:
select是Go语言中的一个控制语句,它有select,case, default共同构成,与switch的书写方式类似。
select只用来操作的channel的读写操作。
(备注:golang 的 select 本质上,就是监听 IO 操作,当 IO 操作发生时,触发相应的动作。也是常用的多路复用的一种,例如poll, epoll(这个会在另外一个帖子中介绍), select )
例子:
select 的特性:
1. 如果只有一个 case 语句评估通过,那么就执行这个case里的语句
2. 如果有多个 case 语句评估通过,那么通过伪随机的方式随机选一个
3.如果 default 外的 case 语句都没有通过评估,那么执行 default 里的语句
4.如果没有 default,那么 代码块会被阻塞,直到有一个 case 通过评估;否则一直阻塞
特性1: select正常case能够评估通过的例子:
特性4: 没有default分支,select被阻塞住的例子:
对比特性1,会发现,select在探测不到case是接收c1数据的情况下,会阻塞在哪里,不会打印"go end!"
特性3: 有default的例子:
select存在default的话,在case不命中的情况下,会直接进入default分支,协程一样会结束,不会阻塞住。
特性2: 多个case 同时满足的情况,会随机选择一个case
通过输出我们可以看出来,尽管channel c1和c2基本是同时写的数据到channel中,但是select选择了c2,忽略了c1。
三、select的应用场景
在看完了select的特性之后,笔者知道了channel的使用方式。可是到底什么时候使用select呢?于是笔者便问了自己另外一个问题。
select的应用场景都有那些,为什么我们需要select?
场景一:实现非阻塞读写操作。
根据select的特性3(如果 default 外的 case 语句都没有通过评估,那么执行 default 里的语句), 我们可以实现非阻塞的读写操作。
这种情况,一般是发生在服务器在给用户推送数据之后,不希望用户一直阻塞在读操作上面。代码实例参考特性3的例子,我们利用default来跳过这个阻塞过程。
场景二: 为请求设置超时时间。
这一个场景也就是前言介绍里面提到的协程通讯时候,长时间收不到读写操作,导致协程一直被阻塞的情况,而超时机制则是一个很常规的操作。我们来看下例子:
1.复现channel阻塞的例子:
2.超时处理的例子:
例子1,因为channel中没有数据可读,导致协程一直阻塞住,并没有go end的日志打印出来。
例子2, 虽然channel 中依然没有数据可读,但是我们实现了超时机制,在2s超时之后,select会触发超时相关的channel,进而结束协程go的阻塞,打印出go end日志。
场景三: 调度协程,控制其他协程的退出或者完成
在并发程序中,通常 main goroutine 将任务分给其它 goroutine 去完成,而自身只是起到调度作用。这种情况下,main goroutine无法知道 其它goroutine 任务是否完成,此时我们需要 done channel来协助完成。
例子为:
不实用done channel的方式,会发现main的goroutinue并不会等待其他的goroutine结束之后,才结束,也不知道其他的goroutiue何时结束。
添加了done channel之后,main goroutinue可以等待其他的goroutinue结束之后,再结束。
备注:对于select的实现机制,这个在后面的文章中介绍。
Go Channel 详解: https://colobu.com/2016/04/14/Golang-Channels/
Go语言并发模型:使用 select:https://segmentfault.com/a/1190000006815341
灰子学技术,欢迎关注,点评,相互学习。
golang select default continue_Go并发(四):select篇相关推荐
- python 高并发 select socket_socket + select 完成伪并发操作的实例
实例如下: #!/usr/bin/env python # -*- coding: utf-8 -*- import socket #创建一个socket对象 sk1 = socket.socket( ...
- 并发编程应用场景_linux网络编程之select函数的并发限制和poll函数应用举例
一.用select实现的并发服务器,能达到的并发数,受两方面限制 1.一个进程能打开的最大文件描述符限制.这可以通过调整内核参数.可以通过ulimit -n来调整或者使用setrlimit函数设置, ...
- 《嵌入式系统 – 玩转ART-Pi开发板(基于RT-Thread系统)》第9章 基于Select/Poll实现并发服务器(二)
基于Select/Poll实现并发服务器(一) 9.3 Select/Poll概述 在LWIP中,如果要实现并发服务器,可以基于Sequentaial API来实现,这种方式需要使用多线程,也就是为每 ...
- UNIX网络编程——select函数的并发限制和 poll 函数应用举例
http://blog.csdn.net/chenxun_2010/article/details/50489577 一.用select实现的并发服务器,能达到的并发数,受两方面限制 1.一个进程能打 ...
- select函数的并发限制和 poll 函数应用举例
一.用select实现的并发服务器,能达到的并发数,受两方面限制 1.一个进程能打开的最大文件描述符限制.这可以通过调整内核参数.可以通过ulimit -n来调整或者使用setrlimit函数设置, ...
- 彻底搞懂 select/poll/epoll,就这篇了!
之前已经把网络 I/O 相关要点都盘了,还剩 select/poll/epoll 这几个区别没说,这篇就来搞搞它们,并且是从完全理解原理的角度来区分它们. 本来是要上源码的,但是感觉没啥必要,身为应用 ...
- golang笔记16--go语言并发版爬虫
golang笔记16--go语言并发版爬虫 1 介绍 2 并发版爬虫 2.1 并发版爬虫架构 2.2 简单调度器 2.3 并发调度器 2.4 队列实现调度器 2.5 重构和总结 2.6 更多城市 2. ...
- PostgreSQL SELECT INTO和INSERT INTO SELECT 两种表复制语句
SELECT INTO和INSERT INTO SELECT两种表复制语句都可以用来复制表与表之间的数据,但是它们之间也有区别. 建表语句: bas_custom_rel表 CREATE TABLE ...
- layui select 修改_layui怎么修改select的值?
layui怎么修改select的值?下面本篇文章给大家介绍一下.有一定的参考价值,有需要的朋友可以参考一下,希望对大家有所帮助. 动态设置layui的select值 html5中加上下类代码获取初始值 ...
最新文章
- 提高你的Java代码质量吧:如果有必要,使用变长数组吧
- 【UAV】高度控制代码分析
- asterisk架构
- CuteEditor6.0使用配置心得体会(转)
- Nacos内核设计之一致性协议
- tomcat和nginx配置java服务器
- 网页粒子背景插件 -Canvas-nest.js
- 这位曾指责乔布斯的怪老头,推出的AppleScript比Windows还要快!
- python数据存储系列教程——python中mongodb数据库操作:连接、增删查改、多级路径
- The method getContextPath() is undefined for the type ServletContext
- 【Plesk经验分享】无法创建备份怎么办?
- dbf解析_JAVA解析DBF文件方案.pdf
- perl 中使用 cpan 工具
- 四川一度智信:电商平台商品关键词优化技巧
- python 批量读取csv_Python Pandas批量读取csv文件到dataframe的方法
- Check Point设置允许外网通过指定端口访问服务器
- 工作中遇到的常见问题
- Day17(集合)学习记录(HashSet集合 HashMap集合)
- Android 高德地图so包太大,高德地图sdk配置心得(jar文件与so文件导入)
- 如何解决数组下标越界异常
热门文章
- wxWidgets:添加状态栏
- wxWidgets:wxVariant类用法
- wxWidgets:wxMiniFrame类用法
- boost::mpl模块实现sizeof相关的测试程序
- boost::math::differentiation用法的测试程序
- boost::r_c_shortest_paths用法的测试程序
- Boost:fork守护程序的测试程序
- ITK:灰度图像中的聚类像素
- ITK:重新运行管道不断变化的最大可能的地区
- ITK:在向量容器上迭代