美文网首页
Go 并发之读写锁

Go 并发之读写锁

作者: 三梦哥 | 来源:发表于2020-03-02 10:42 被阅读0次

在业务当中我们常常需要遇到并发读写,其中读的频率远大于写的频率的情况,对数据的写入是需要互斥的,也就是同时只能允许一个线程去修改某个数据,但是允许多个读线程同时去读取某个数据。总的来说就是:

  • 当有一个写线程来修改某个临界量的时候,不允许其它的写线程和读线程来进入临界区;
  • 当有一个读线程来读取某个临界量的时候,不允许其它的写线程进入临界区,但允许其它的读线程来进入临界量;

对比互斥锁和读写锁

当使用sync.Mutex 来实现并发同步

使用sync.Mutex来对读线程和写线程来进行互斥操作,代码如下:

package main

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

var (
    wg   sync.WaitGroup
    lock sync.Mutex
    data int64
)

func read() {
    defer lock.Unlock()
    defer wg.Done()
    lock.Lock()
    time.Sleep(time.Millisecond) //模拟读取耗时
}

func write() {
    defer lock.Unlock()
    defer wg.Done()
    lock.Lock()
    data++
}

func main() {
    start := time.Now()
    for i := 0; i < 1000; i++ {
        wg.Add(1)
        go read()
    }
    for i := 0; i < 10; i++ {
        wg.Add(1)
        go write()
    }
    wg.Wait()
    fmt.Println(data)
    d := time.Now().Sub(start)
    fmt.Println(d)
}

结果输出如下:

互斥锁
容易看出,耗时1.5s

当使用sync.RWMutex来实现并发同步

使用sync.RWMutex来对读线程和写线程来进行互斥操作,代码如下:

package main

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

var (
    wg   sync.WaitGroup
    lock sync.RWMutex
    data int64
)

func read() {
    defer lock.RUnlock()
    defer wg.Done()
    lock.RLock()
    time.Sleep(time.Millisecond) //模拟读取耗时
}

func write() {
    defer lock.Unlock()
    defer wg.Done()
    lock.Lock()
    data++
}

func main() {
    start := time.Now()
    for i := 0; i < 1000; i++ {
        wg.Add(1)
        go read()
    }
    for i := 0; i < 10; i++ {
        wg.Add(1)
        go write()
    }
    wg.Wait()
    fmt.Println(data)
    d := time.Now().Sub(start)
    fmt.Println(d)
}

结果输出如下:


读写锁

容易看出,耗时7ms

总结

方式 sync.Mutex sync.RWMutex
耗时 1.5s 7ms

所以在遇到并发读写,并且读的频率远大于写的频率的时候,需要使用sync.RWMutex读写锁来实现读写并发。

相关文章

  • Go 并发之读写锁

    在业务当中我们常常需要遇到并发读写,其中读的频率远大于写的频率的情况,对数据的写入是需要互斥的,也就是同时只能允许...

  • Go语言高并发Map解决方案

    Go语言高并发Map解决方案 Go语言基础库中的map不是并发安全的,不过基于读写锁可以实现线程安全;不过在Go1...

  • java并发之ReentrantReadWriteLock

    java并发之ReentrantReadWriteLock 知识导读 读写锁内部维护了两个分离的锁,读锁和写锁,两...

  • golang 基础(31) 锁

    在 go 语言中提供了并发编程模型和工具外,还提供传统的同步工具锁,包括互斥锁和读写锁有关互斥锁有些内容我们必须清...

  • Go 语言的锁

    Go 语言提供两类锁: 互斥锁(Mutex)和读写锁(RWMutex)。其中读写锁(RWMutex)是基于互斥锁(...

  • 1.MySQL的架构与历史

    MySQL逻辑架构 并发控制 读写锁sharelock共享锁,exclusivelock排他锁 锁粒度table ...

  • Go并发编程之美-读写锁

    一、前言 go语言类似Java JUC包也提供了一些列用于多线程之间进行同步的措施,比如低级的同步措施有 锁、CA...

  • ZooKeeper实现读写锁

    1 读写锁的概念 读写锁是计算机程序的并发控制的一种同步机制,用于解决读写问题,读操作可并发重入,写操作是互斥的。...

  • Go 并发之互斥锁

    在 Go 语言中使用sync.Mutex 来实现互斥锁,示例代码如下: 输出结果为:

  • Go 读写锁

    读写锁sync.RWMutext实现读者写者问题

网友评论

      本文标题:Go 并发之读写锁

      本文链接:https://www.haomeiwen.com/subject/caqpkhtx.html