1. 简介
goroutine
是 Go
中的并发执行单位,可以理解为“线程”,但它不是“线程”。生成一个 goroutine
非常简单,只需 go
一下就实现了。在同一个程序中所有的 goroutine
共享一个地址空间。goroutine
通过通信来共享内存,而不是共享内存来通信。
channel
是各个 goroutine
之间通信的管道,它是引用类型,可以使用 ==
进行比较,如果引用了相同的数据结构,则结果为真。传数据用 channel <- data
,取数据用 <- channel
。多数情况下,它是阻塞同步的。channel
可以设置为单向或双向,也可以设置缓存大小,在未被填满前不会发生阻塞。
select
可处理一个或多个 channel
的发送与接收,同时有多个可用的 channel
时按随机顺序处理。
2. 基本使用
样例 1 :
1 | package main |
go func()
启动了一个 goroutine
,main
函数执行到 <- ch
时会一直等待直到取得管道中的值,当打印出 “Go go go!“ 之后,才会传递值到管道中,这时候,程序才执行结束。这是一个简单的示例,我们不需要手动关闭管道,程序结束后占用的资源会自动释放。
样例 2 :
1 | package main |
for range
会不断地迭代管道中的值,知道管道被关闭。如果我们删掉 close(ch)
这行代码,会导致死锁。
2. 设置缓存
无缓存是同步阻塞的,有缓存是异步的。
样例 3 :
1 | package main |
上例设置了一个缓存为 10 的管道,实现了多个 goroutine
的并发执行。除了 channel
,我们还可以用 WaitGroup
实现同样的效果,见样例 4 。
样例 4 :
1 | package main |
3. select 的用法
select
是 Go
中的一个控制结构,类似于用于通信的 switch
语句。每个 case
必须是一个只能用于 channel
的通信操作,要么是发送要么是接收。
select
如果满足多个分支条件,则会随机执行一个 case
。如果没有 case
可运行,它将阻塞,直到有 case
可运行。一个默认的子句应该总是可运行的。
样例 5 :
1 | package main |
样例 6 :
1 | package main |