Go中的sync包如何用于并发控制?

东白随记
0 评论
/ /
0 阅读
/
2211 字
07 2024-09

在Go语言中,`sync`包提供了用于并发控制的工具和机制。这个包提供了互斥锁(Mutex)和条件变量(Cond)等基本的数据结构,以及一些其他用于同步的函数和类型。

以下是`sync`包中一些常用的并发控制工具及其使用方法:

1. 互斥锁(Mutex):

互斥锁用于保护共享资源,确保同一时间只有一个goroutine可以访问共享资源。通过使用`sync.Mutex`类型,可以控制对共享资源的访问。

示例:

```go

import "sync"

var mutex sync.Mutex // 定义一个互斥锁

func doSomething() {

mutex.Lock() // 加锁,阻止其他goroutine访问共享资源

// 执行对共享资源的操作

mutex.Unlock() // 解锁,允许其他goroutine访问共享资源

}

```

2. 读写锁(RWMutex):

读写锁允许多个goroutine同时读取共享资源,但只允许一个goroutine写入。这对于读操作远多于写操作的场景非常有用。

示例:

```go

import "sync"

var rwMutex sync.RWMutex // 定义一个读写锁

func readSomething() {

rwMutex.RLock() // 加读锁,允许多个goroutine同时读取共享资源

// 执行读取操作

rwMutex.RUnlock() // 解锁读锁

}

func writeSomething() {

rwMutex.Lock() // 加写锁,阻止其他goroutine读取或写入共享资源

// 执行写入操作

rwMutex.Unlock() // 解锁写锁

}

```

3. 等待组(WaitGroup):

`sync.WaitGroup`用于等待一组goroutine完成执行。它允许你等待一组并发执行的goroutine完成,然后继续执行其他操作。

示例:

```go

import "sync"

var wg sync.WaitGroup // 定义一个等待组

func doWork() {

wg.Add(1) // 增加等待组的计数器,表示有一个goroutine正在执行任务

// 执行任务逻辑...

wg.Done() // 表示任务完成,减少等待组的计数器

}

func main() {

for i := 0; i < 10; i++ { // 启动多个goroutine执行任务... } wg.Wait() // 等待所有goroutine完成执行 }`

4. 条件变量(Cond):`sync.Cond`用于在多个goroutine之间进行条件同步。它允许一个或多个goroutine在满足特定条件时被唤醒或阻塞。通常与互斥锁一起使用,以确保在修改条件时互斥访问共享资源。示例:```go import "sync" var mu sync.Mutex var cond = sync.NewCond(&mu) // 定义一个互斥锁和一个条件变量 func waitForSignal() { mu.Lock() // 加锁 defer mu.Unlock() // 在释放锁之前,使用条件变量等待信号 cond.Wait() // 等待信号 } func sendSignal() { mu.Lock() // 加锁 if someCondition { // 检查条件是否满足 mu.Unlock() // 如果条件满足,解锁并唤醒一个等待的goroutine return } // 其他逻辑 mu.Unlock() // 如果条件不满足,则继续其他逻辑 cond.Signal() // 发送信号 } ```在这个示例中,`waitForSignal`函数在满足某个条件之前会一直等待。当其他goroutine中的`sendSignal`函数检查到条件满足时,会通过调用`cond.Signal()`来唤醒等待的goroutine。注意,在使用条件变量时,必须始终在互斥锁的保护下进行操作,以确保线程安全。