gpt4 book ai didi

go - Golang 中的 RLock() 和 Lock() 有什么区别?

转载 作者:IT王子 更新时间:2023-10-29 02:27:01 25 4
gpt4 key购买 nike

Golang 中的 RLock() 和 Lock() 有什么区别,我们在使用互斥锁时如何有效地使用它们?

最佳答案

Lock():通过获取锁,一次只能进行一次读/写。

RLock():多个go routine可以通过获取锁同时读取(不能写入)。

package main

import (
"fmt"
"sync"
"time"
)

func main() {

a := 0

lock := sync.RWMutex{}

for i := 1; i < 10; i++ {
go func(i int) {
lock.Lock()
fmt.Printf("Lock: from go routine %d: a = %d\n",i, a)
time.Sleep(time.Second)
lock.Unlock()
}(i)
}

b := 0

for i := 11; i < 20; i++ {
go func(i int) {
lock.RLock()
fmt.Printf("RLock: from go routine %d: b = %d\n",i, b)
time.Sleep(time.Second)
lock.RUnlock()
}(i)
}

<-time.After(time.Second*10)
}

1) 当一个 go-routine 已经获取了一个 RLock() 时,另一个 go-routine 是否可以获取一个 Lock() 进行写入,或者它必须等到 RUnlock() 发生?

  • 要获取用于写入的 Lock(),它必须等到 RUnlock()

2) 当有人已经为 map 获取了 Lock() 时会发生什么,其他 go-routine 是否仍然可以获取 RLock()

  • 如果某人 X 已经获取了 Lock(),那么其他获取 RLock() 的 go-routine 将不得不等到 X 释放锁(Unlock())

3) 假设我们在这里处理Maps,是否有可能出现“并发读/写Map”错误?

  • Map 不是线程安全的。所以“ map 的并发读/写”会导致错误。

请参阅以下示例以获得更多说明:

package main

import (
"fmt"
"sync"
"time"
)

func main() {
lock := sync.RWMutex{}

b := map[string]int{}
b["0"] = 0

go func(i int) {
lock.RLock()
fmt.Printf("RLock: from go routine %d: b = %d\n",i, b["0"])
time.Sleep(time.Second*3)
fmt.Printf("RLock: from go routine %d: lock released\n",i)
lock.RUnlock()
}(1)

go func(i int) {
lock.Lock()
b["2"] = i
fmt.Printf("Lock: from go routine %d: b = %d\n",i, b["2"])
time.Sleep(time.Second*3)
fmt.Printf("Lock: from go routine %d: lock released\n",i)
lock.Unlock()
}(2)

<-time.After(time.Second*8)

fmt.Println("*************************************8")

go func(i int) {
lock.Lock()
b["3"] = i
fmt.Printf("Lock: from go routine %d: b = %d\n",i, b["3"])
time.Sleep(time.Second*3)
fmt.Printf("Lock: from go routine %d: lock released\n",i)
lock.Unlock()
}(3)

go func(i int) {
lock.RLock()
fmt.Printf("RLock: from go routine %d: b = %d\n",i, b["3"])
time.Sleep(time.Second*3)
fmt.Printf("RLock: from go routine %d: lock released\n",i)
lock.RUnlock()
}(4)

<-time.After(time.Second*8)
}

关于go - Golang 中的 RLock() 和 Lock() 有什么区别?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/53427824/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com