Go语言程序设计-第9章--使用共享变量实现并发

Go语言程序设计-第9章--使用共享变量实现并发

9.1 竟态

一个能在串行程序中正确工作的函数。如果这个函数在并发调用时仍然能正确工作,那么这个函数是并发安全的。在这里并发调用是指,在没有额外同步机制的情况下,从两个或者多个 goroutine 同时调用这个函数。如果一个类型的所有可访问方法和操作都是并发安全时,则它可称为并发安全的类型。

数据竟态发生于两个 goroutine 并发读写同一个变量,并且至少一个是写入时。有3个方法避免数据竟态。

第一种方法是不要修改变量。

第二种方法是避免多个 goroutine 访问同一个变量。

第三种方法是允许多个 goroutine 访问同一个变量,但是在同一时间只有一个 goroutine 可以访问,这种方法称为互斥机制。

9.2 互斥锁:sync.Mutex

在 Mutex 的 Lock 和 Unlock 之间,可能自由地读取和修改共享变量,这一部分称为临界区域。

9.3 读写互斥锁:sync.RWMutex

仅在绝大部分 goroutine 都在获取读锁并且锁竞争比较激烈时,RWMutex 才有优势。

9.4 内存同步

现代计算机一般会有多个处理器,每个处理器都有内存的本地缓存。为了提高效率,对内存的写入是缓存在每个处理器中的,只有在必要时才刷回内存。甚至刷回内存的顺序都可能与 goroutine 的写入顺序不一致。像通道或者互斥锁操作这样的同步原语都会使处理器把积累的写操作刷回内存并提交。

9.5 延迟初始化: sync.Once

go 复制代码
var loadIconsOnce sync.Once
var icons map[string]image.Image
// 并发安全
func Icon(name string) image.Image {
	loadiconsOnce.Do(loadIcons)
	return icons[name]
}

9.6 竟态检测器

把 -race 命令行添加到 go build, go run, go test 命令里面即可以使用该功能。

9.8 goroutine 与线程

9.8.1 可增长的栈

每个 OS 线程都有一个固定大小的栈内存(通常为 2MB),栈内存区域用于保存在其他函数调用期间哪些正在执行或临时暂停函数中的局部变量。这个固定的栈大小既又太大又太小。对于一个小的 goroutine,2MB的栈是一个巨大的浪费。对于复杂的和深度递归的函数,固定大小的栈始终不够大。

作为对比,一个 goroutine 在生命周期开始只有一个很小的栈,典型情况下为 2KB。与 OS 线程不同的是,goroutine 的栈不是固定大小的,它可以按需增大和缩小。goroutine 的栈可以到达 1GB,比线程典型的固定大小栈高出几个数量级。

Go 运行时包含一个自己的调度器,这个调度器使用一个称为 m:n 调度的技术(因为它可以复用/调度 m 个 goroutine 到 n 个 OS 线程)。Go 调度器与内核调度器的工作类似,但只关心单个 Go 程序的 goroutine 调度问题。

9.8.3 GOMAXPROCS

Go 调度器使用 GOMAXPROCS 参数确定使用多少个 OS 线程来同时执行 Go 代码。默认值是机器上 CPU 的数量。

bash 复制代码
GOMAXPROCS=1 go run hack-cliche.go

9.8.4 goroutine 没有标识

所以没有线程本地变量之类的结构。

相关推荐
鲤籽鲲1 分钟前
C# MethodTimer.Fody 使用详解
开发语言·c#·mfc
亚图跨际5 分钟前
Python和R荧光分光光度法
开发语言·python·r语言·荧光分光光度法
Rverdoser13 分钟前
RabbitMQ的基本概念和入门
开发语言·后端·ruby
dj244294570716 分钟前
JAVA中的Lamda表达式
java·开发语言
流星白龙1 小时前
【C++习题】10.反转字符串中的单词 lll
开发语言·c++
尘浮生1 小时前
Java项目实战II基于微信小程序的校运会管理系统(开发文档+数据库+源码)
java·开发语言·数据库·微信小程序·小程序·maven·intellij-idea
MessiGo1 小时前
Python 爬虫 (1)基础 | 基础操作
开发语言·python
Tech Synapse1 小时前
Java根据前端返回的字段名进行查询数据的方法
java·开发语言·后端
.生产的驴1 小时前
SpringCloud OpenFeign用户转发在请求头中添加用户信息 微服务内部调用
spring boot·后端·spring·spring cloud·微服务·架构
乌啼霜满天2491 小时前
JDBC编程---Java
java·开发语言·sql