文档章节

简单看懂GO语言并发

Cheuker
 Cheuker
发布于 2017/08/03 13:58
字数 718
阅读 29
收藏 0

并发基础

GO语言处理并发非常简单,使用关键词“go”即可。

创建main.go文件,内容如下:

package main

func main() {
	go print(1)
}

这是一个非常简单的并发例子。运行 go run main.go,你会发现什么也不会输出。为什么?因为没等print执行,主程就退了。

我们把代码修改下:

package main

import "time"

func main() {
	go print(1)
	time.Sleep(time.Second)
}

这里停了一秒,使得print有足够的时间输出后结束。假设print执行超过一秒钟,或者我们压根不知道print要执行多少时间,这是后我们就要要到“channel”啦。

package main

import (
	"fmt"
	"time"
)

func main() {
	done := make(chan bool)
	go Print(1, done)
	for {
		<-done
		break
	}
}

func Print(args interface{}, done chan bool) {
	time.Sleep(time.Second * 3)
	fmt.Println(args)
	done <- true
}

无论我们怎么调整sleep的参数,程序都会等待print输出后才结束。到这里我们想如果Print 3秒钟后还没执行我们就要退出了,这里就可以用到channel的一个超时处理方式:

package main

import (
	"fmt"
	"time"
)

func main() {
	done := make(chan bool)
	isTimeOut := make(chan bool)
	go Print(1, done)
	go func(){
		time.Sleep(time.Second*3)
		isTimeOut <- true
	}()
	for {
		select {
		case <-done:
			return
		case <-isTimeOut:
			println("timeout.")
			return
		}
	}
}

func Print(args interface{}, done chan bool) {
	time.Sleep(time.Second * 5)
	fmt.Println(args)
	done <- true
}

这里go run main.go输出"timeout."。我们可以设置缓冲,如:

result := make(chan int,10)

result一开始会存入10个元素,阻塞直到result的元素被取出且小于10后才能再往result写入数据。

并发应用

使用go并发我们可以进行任务分发:

package main

import (
	"fmt"
)

func main() {
	result := make(chan int)
	rlt := 0
	go Sum(1, 50, result)
	go Sum(51, 100, result)
	//把两次写入到result的值取出来求和
	for i := 1; i <= 2; i++ {
		rlt += <-result
	}
	fmt.Println(rlt)
}

func Sum(start, end int, result chan int) {
	sum := 0
	for i := start; i <= end; i++ {
		sum += i
	}
	result <- sum
}

这里计算1+2+3+..+100的和,并发两个进程处理。当然这里为了演示不考虑算法问题了。

使用GO并发构建工作池,工作池就是能进行特定功能处理的“工人”的集合。这里的“工人”可以理解为我们封装好的函数比如上面sum。看下简单的一个示例:

package main

import (
	"fmt"
)

func main() {
	start, end := make(chan int), make(chan int)
	//启动有五个工人的工作池
	for i := 0; i <= 4; i++ {
		go Sum(i, start, end)
	}
	//发送任务给工作池中工人处理
	for i := 1; i <= 5; i++ {
		start <- i * 5
		end <- i * 10
	}
}

func Sum(worker int, start, end chan int) {
	sum := 0
	s := <-start
	e := <-end
	for i := s; i <= e; i++ {
		sum += i
	}
	fmt.Println("worker ", worker, " -> ", sum)
}

每次go run main.go输出的顺序,结果可能都不一样:

worker  4  ->  45
worker  2  ->  360
worker  1  ->  165
worker  3  ->  630
worker  0  ->  975
worker  4  ->  45
worker  1  ->  165
worker  3  ->  360
worker  0  ->  630
worker  2  ->  975

可以看出,只要哪个“工人”通道中获取到需要计算的值,谁就先处理。

© 著作权归作者所有

Cheuker
粉丝 0
博文 24
码字总数 5727
作品 0
厦门
高级程序员
私信 提问
优秀的架构师需要那些专业和软技能?

这段时间时间一直在想,优秀的架构师需要那些专业和软技能?参考了网上一个资料并结合自己的切身体会和想法,分享如下,希望能对同道中的朋友有所帮助。 # 专业技能 @面向对象的OOP理解,真正...

chancein007
2016/12/19
0
0
看文档还是看源代码+调试--附带rsyslog的例子

看源代码要比看文档高效多了。文档是用自然语言写的,比如英语,日语,中文等等,文化的差异以及各种语法的不同使得文档理解起来很不方便,再说很多人根本就没有外语阅读的能力。自然语言还是...

晨曦之光
2012/04/10
724
0
博客阅读整理一

(部分文章是系列文章,可在原文博客查找) Java ClassLoader, JavaAgent, Aspectj Weaving一站式扫盲帖:主要总结了ClassLoader、java代理、反射相关的知识点 jdbc实现篇-源码:介绍了jdbc的源...

oO脾气不坏Oo
2015/10/17
91
0
Haskell 2014.2 发布,函数式编程语言

函数式编程语言 Haskell 2014.2 发布了,改进记录请看 changelog (表示没看懂) Haskell是一种纯函数式编程语言,它的命名源自美国数学家Haskell Brooks Curry,他在数学逻辑方面上的工作使...

oschina
2014/08/11
2.5K
13
商用编程语言--COBOL

COBOL(面向商业的通用语言,又称为企业管理语言、数据处理语言等,Common Business Oriented Langauge)是最早的高级编程语言之一,是世界上第一个商用语言。 COBOL是一种面向数据处理的、面...

匿名
2009/04/12
12.1K
1

没有更多内容

加载失败,请刷新页面

加载更多

springboot 403 问题

添加WebAppConfigurer 配置 @Configuration@EnableAutoConfigurationpublic class WebAppConfigurer extends WebMvcConfigurerAdapter { public WebAppConfigurer() { } ......

布袋和尚_爱吃鱼
25分钟前
3
0
Python自动更换壁纸爬虫与tkinter结合

直接上代码 import ctypesimport timeimport requestsimport osfrom threading import Threadfrom tkinter import Tk, Label, Button,Entry,StringVar,messagebox# '放到AppData\Roami......

物种起源-达尔文
26分钟前
3
0
Postgresql Study 笔记

Postgresql 安装 Windows, MAC Install Postgresql 下载地址: https://www.enterprisedb.com/downloads/postgres-postgresql-downloads Linux Install sudo apt-get update sudo apt-get in......

slagga
27分钟前
4
0
layer.open 打开新页面传参问题

如图所示,点击出售,把A页面的数据传到弹框上面,因为弹框比较复杂,所以使用引入一个新页面。 A.html a.js B.html b.js 1、第一种方案 sellInte: function (){ var obj = document.g...

木九天
30分钟前
4
0
沙龙报名 | 区块链数据服务技术应用实践

京东云是国内首家提供区块链数据在线分析服务产品的公司,也是行业内首家对区块链数据服务进行开源的公司。 本次沙龙是京东云BDS开源后,首次在深圳举办线下沙龙,我们将邀请京东云BDS团队核...

京东云技术新知
31分钟前
4
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部