github.com/gitbookio/syncgroup@v0.0.0-20181003125046-3e73b2e6a972/sharded.go (about) 1 package syncgroup 2 3 import ( 4 "sync" 5 6 "github.com/GitbookIO/syncgroup/quickhash" 7 ) 8 9 // ShardedMutexes shards calls to a list of sync.RWMutex by key 10 type ShardedMutexes struct { 11 shards []*sync.RWMutex 12 n uint64 13 } 14 15 func NewShardedMutexes() *ShardedMutexes { 16 var n uint64 = 2048 17 shards := make([]*sync.RWMutex, n) 18 // Init shard 19 for idx, _ := range shards { 20 shards[idx] = &sync.RWMutex{} 21 } 22 23 return &ShardedMutexes{ 24 shards: shards, 25 n: n, 26 } 27 } 28 29 func (sg *ShardedMutexes) Lock(key string) { 30 sg.getShard(key).Lock() 31 } 32 33 func (sg *ShardedMutexes) RLock(key string) { 34 sg.getShard(key).RLock() 35 } 36 37 func (sg *ShardedMutexes) Unlock(key string) { 38 sg.getShard(key).Unlock() 39 } 40 41 func (sg *ShardedMutexes) RUnlock(key string) { 42 sg.getShard(key).RUnlock() 43 } 44 45 func (sg *ShardedMutexes) Locker(key string) *sync.RWMutex { 46 return sg.getShard(key) 47 } 48 49 func (sg *ShardedMutexes) RLocker(key string) *sync.RWMutex { 50 return sg.getShard(key) 51 } 52 53 func (sg *ShardedMutexes) getShard(key string) *sync.RWMutex { 54 hash := quickhash.StrHash(key) 55 return sg.shards[hash%2048] 56 }