当前位置: 首页 > news >正文

郑州建设网站定制明星网站设计论文

郑州建设网站定制,明星网站设计论文,浙江省住房和城乡建设厅网站,东营网站优化go读写锁的实现原理 1、RWMutex读写锁的概念 读写锁也就是我们所使用的RWMutex,其实是对于go本身的mutex做的一个拓展,当一个goroutine获得了读锁后,其他goroutine同样可以获得读锁,但是不能获得写锁。相反,当一个go…

go读写锁的实现原理

1、RWMutex读写锁的概念

读写锁也就是我们所使用的RWMutex,其实是对于go本身的mutex做的一个拓展,当一个goroutine获得了读锁后,其他goroutine同样可以获得读锁,但是不能获得写锁。相反,当一个goroutine获得了写锁,其他goroutine既不能读也不能写,互斥的概念。

2、使用场景

适用于读多写少的情况

3、底层实现

读写锁实现的结构体位于src下的sync包下的rwmutex.go文件中

type RWMutex struct {w           Mutex  // held if there are pending writerswriterSem   uint32 // semaphore for writers to wait for completing readersreaderSem   uint32 // semaphore for readers to wait for completing writersreaderCount int32  // number of pending readersreaderWait  int32  // number of departing readers
}	

w字段代表着复用了互斥锁

writerSem代表写信号量,用于写等待读

readerSem代表读信号量,用于读等待写

readerCount代表当前执行读的goroutine数量

readerWait代表被阻塞的准备读的goroutine的数量

4、读锁的实现

加读锁

func (rw *RWMutex) RLock() {if atomic.AddInt32(&rw.readerCount, 1) < 0 {// A writer is pending, wait for it.runtime_SemacquireMutex(&rw.readerSem, false, 0)}
}

首先看这个if方法,为什么要判断小于0呢?

atomic.AddInt32(&rw.readerCount, 1) < 0调用的这个原子方法,目的就是当goroutine加读锁的时候读锁数量+1,如果返回的数量是负数,那么就代表了当前有其他写锁,这个时候就掉用runtime_SemacquireMutex方法休眠当前goroutine,readerSem就记录者这个goroutine。所以要判断是否小于0

释放读锁

// RUnlock undoes a single RLock call;
// it does not affect other simultaneous readers.
// It is a run-time error if rw is not locked for reading
// on entry to RUnlock.
func (rw *RWMutex) RUnlock() {if r := atomic.AddInt32(&rw.readerCount, -1); r < 0 {// Outlined slow-path to allow the fast-path to be inlinedrw.rUnlockSlow(r)}
}

释放读锁的时候就是对readerCount读数量-1即可,如果返回值小于0,就代表着当前有写的操作,这个时候就会调用rUnlockSlow进入慢速通道

什么是慢速通道

func (rw *RWMutex) rUnlockSlow(r int32) {// A writer is pending.if atomic.AddInt32(&rw.readerWait, -1) == 0 {// The last reader unblocks the writer.runtime_Semrelease(&rw.writerSem, false, 1)}
}

被阻塞的准备读的goroutine数量-1,如果readerWait为0,就表示当前没有goroutine正在准备读,这个时候去唤醒写操作

5、写锁的实现

加写锁

const rwmutexMaxReaders = 1 << 30
// Lock locks rw for writing.
// If the lock is already locked for reading or writing,
// Lock blocks until the lock is available.
func (rw *RWMutex) Lock() {// First, resolve competition with other writers.rw.w.Lock()// Announce to readers there is a pending writer.r := atomic.AddInt32(&rw.readerCount, -rwmutexMaxReaders) + rwmutexMaxReaders// Wait for active readers.if r != 0 && atomic.AddInt32(&rw.readerWait, r) != 0 {runtime_SemacquireMutex(&rw.writerSem, false, 0)}
}

写锁的调用就是调用互斥锁w的lock,如果计算之后还是有其他goroutine持有读锁,那么就调用runtime_SemacquireMutex休眠当前的goroutine等待所有的读操作完成, atomic.AddInt32(&rw.readerCount, -rwmutexMaxReaders) + rwmutexMaxReaders这个操作目的是防止后面的goroutine拿到读锁,阻塞读的作用。

释放写锁

// Unlock unlocks rw for writing. It is a run-time error if rw is
// not locked for writing on entry to Unlock.
//
// As with Mutexes, a locked RWMutex is not associated with a particular
// goroutine. One goroutine may RLock (Lock) a RWMutex and then
// arrange for another goroutine to RUnlock (Unlock) it.
func (rw *RWMutex) Unlock() {// Announce to readers there is no active writer.r := atomic.AddInt32(&rw.readerCount, rwmutexMaxReaders)if r >= rwmutexMaxReaders {race.Enable()fatal("sync: Unlock of unlocked RWMutex")}// Unblock blocked readers, if any.for i := 0; i < int(r); i++ {runtime_Semrelease(&rw.readerSem, false, 0)}// Allow other writers to proceed.rw.w.Unlock()
}

当释放写锁的时候,首先会通过atomic.AddInt32(&rw.readerCount, rwmutexMaxReaders)恢复之前的写入的很大的那个负数,然后看当前有多少个读操作在等待,循环唤醒等待读的goroutine

注意:go中的锁不支持可重入锁,若想实现可自定义实现

6、总结

读写锁区分读锁和写锁,而普通的互斥锁不区分,读写锁主要应用在读多写少的场景,既保证了并发读的执行效率,又保证了线程之间的安全。

http://www.yayakq.cn/news/386391/

相关文章:

  • q网站建设营销策划方案范文1500
  • 中国优秀企业网站公司搭建网站服务
  • 网站权重有什么用天津公司
  • 河北省网站备案步骤软文广告营销
  • 莆田网站制作价格医院网站建设投标书
  • 如何做图让网站的图更清晰中恒诚信建设有限公司网站
  • 廊坊做网站找谁网站建设项目签约仪式举行
  • 企业做网站怎么做网站和自媒体都可以做
  • 校园网站制作方法百度收录提交入口网址
  • 临海网站建设公司做淘宝客网站
  • dw做旅游网站模板下载怎么建一个小说网站
  • 做网站手机端需要pc端的源代码吗燕郊的大型网站建设
  • 单页面网站带后台淮北市建设协会网站
  • 安徽省水利建设厅官方网站网上注册公司核名流程
  • 越秀区pc端网站建设阿里云 邮件 wordpress
  • 福田附件网站建设公司邯郸模板建站教程
  • 网站开发单子北关网站制作
  • 黄岛网站建设设计公司医院网站案例
  • 建设银行在网站上开通短信提醒深圳网站建设服务哪便宜
  • 深圳市工程建设交易服务中心网站wordpress 清空换行
  • 网页设计设计一个网站首页google推广妙招
  • 大同网站建设制作嘉兴做网站优化多少钱
  • 武进网站建设好么建设网站属于什么费用
  • 网站建设运营维护合同seo发包软件
  • jsp网站开发标准怎么做网站弄网盟
  • 潮州 网站建设福建建设科技人才网站
  • 自己做网站自己做SEO网站建设能做什么工作
  • 大连html5网站建设费用含山县城市建设有限公司网站
  • 福清可以做宣传的网站华为企业文化
  • wordpress 主机屋seo推广方式