golang 碎片整理之幸运飞艇程序制作并发

并发:同一时间段内执行多个任务。
并行:同一时刻执行多个任务。

幸运飞艇程序制作q<115.28.8.00.9.9>

Go语言的并发通过goroutine实现。goroutine类似于线程,属于用户态的线程,我们可以根据需要创建成千上万个goroutine并发工作。goroutine是由go语言的运行调度完成的,而线程是由操作系统调度完成的。
Go语言还提供了channel在多个goroutine间进行通信。goroutine和channel是go语言秉承的CSP(Communicating Sequential Process)并发模式的重要实现基础。

goroutine
在Java/c++中我们要实现并发编程的时候,我们通常要自己维护一个线程池,并且需要自己去包装一个又一个的任务和然后自己去调度线程执行任务并维护上线文的切换,这一切通常会耗费程序员的大量心智。能不能有一种机制,程序员只需要定义很多个任务,让系统去帮忙我们把这些任务分配到CPU上实现并发执行呢? Go语言中的goroutine就是这样一种机制,Go语言之所以能被称为现代化的编程语言,就是因为它在语言层面已经内置了调度和上下文切换的机制。

使用goroutine
Go程序中使用go关键字为一个函数创建一个goroutine。一个函数可以被创建多个goroutine,一个goroutine必定对应一个函数。

启动单个goroutine
启动goroutine的方式非常简单,只需要在调用的函数(普通函数和匿名函数)前面加一个go 关键字。
举个例子:

package main

import (
"fmt"
)

func hello() {
fmt.Println("hello goroutine")
}
func main() {
hello()
fmt.Println("main goroutine done!")
}
这个示例中hello函数和下面的语句是串行的,执行的结果是打印完hello goroutine 后打印main goroutine done!
接下来我们在调用hello 函数前面加上go关键字,也就是启动一个goroutine区执行hello这个函数。

func main() {
go hello()
fmt.Println("main goroutine done!")
}
这一次的执行结果只打印了 main goroutine done! , 并没有打印 hello goroutine,为什么呢?
在程序启动时,Go程序就会为main()函数创建一个默认的goroutine。当main函数返回的时候该goroutine就结束了,所有在main()函数中启动的goroutine 会一同结束,main函数所在的goroutine就像是权利的游戏中的夜王,其他的goroutine就像是异鬼,夜王一死它转化的那些异鬼也就全部GG了。
所以我们要想办法让main函数等一等hello函数,最简单粗暴的方式就是sleep了。

func main(){
go hello()
fmt.Println("main goroutine done!")
time.Sleep(time.Second)
}
执行上面的代码你会发现,这一次先打印main goroutine done! ,然后紧接着打印Hello Goroutine!
首先为什么会打印main goroutine done! 是因为我们在创建新的goroutine 的时候需要花费一些时间,而此时main函数所在的goroutine是继续执行的。

猜你喜欢

转载自www.cnblogs.com/jihuazhong/p/11250201.html
今日推荐