我一直在使用RWLock对mysql数据库进行读取,但是在等待解锁时,下面的代码似乎间歇地锁定程序?
// Returns string value from key in table specified, third parameter should be set to false if it shouldn't be case senstive.
func (self *DBStore) GetString(table string, key string, vargs...interface{}) (output string) {
defer func() { fmt.Println("GETSTRING Freeing Mutex!") }()
self.mutex.RLock()
fmt.Println("GETSTRING Got Mutex!")
defer self.mutex.RUnlock()
self.Get(table, key, &output, vargs...)
return
}
// Retreive a value at key in table specified.
func (self *DBStore) Get(table string, key string, output interface{}, vargs...interface{}) (found bool) {
defer func() { fmt.Println("GET Freeing Mutex!") }()
fmt.Println("Requesting Mutex")
self.mutex.RLock()
fmt.Println("GET Got Mutex!")
defer self.mutex.RUnlock()现在,我可以看到,我真的不需要在这里执行RLock,我只需简单地删除它,但我的印象是读锁不应该干扰另一个读锁。而且,它似乎是间歇性的,而且通常需要我运行几次相同的事情才能再次发生。
程序的输出是:
Requesting Mutex
GET Got Mutex!
GET Freeing Mutex!
GETSTRING Got Mutex!
Requesting Mutex然后它就会永远地被锁着。我在这里错过了什么?
任何信息都将不胜感激!
go版本go1.4达尔文/amd64 64
发布于 2015-01-22 06:20:57
在考虑了背靠背RLock的问题之后,这是有意义的。
我在这里不记录的是锁,现在清楚的是,一个锁正在进入背靠背RLocks之间。
基本上锁是排队的。
(Thread 1) GetString -> Request Read Lock
(Thread 1) GetString -> Got Read Lock
(Thread 2) Set -> Request Write Lock (Blocked, queued.)
(Thread 1) Get -> Request Read Lock (Blocked, queued.)来自http://golang.org/src/sync/rwmutex.go?s=862:888#L19
34如果atomic.AddInt32(&rw.readerCount,1) <0{ 35 // A写入器正在等待,请等待它。36 runtime_Semacquire(&rw.readerSem) 37 }
https://stackoverflow.com/questions/28081740
复制相似问题