映射并发访问

当你在并发访问的程序中使用映射时,是否需要在函数中使用互斥来读取值?

多读者,没有作家是好的:

https://groups.google.com/d/msg/golang-nuts/HpLWnGTp-n8/hyUYmnWJqiQJ

一个作家,没有读者可以。 (否则地图不会太好。)

否则,如果至less有一个作者和至less一个作者或读者,则所有读者作者都必须使用同步来访问地图。 互斥量对此很好。

sync.Map 2017年4月27日起, sync.Map已合并到Go master。

这是我们一直在等待的并发地图。

https://github.com/golang/go/blob/master/src/sync/map.go

https://godoc.org/sync#Map

我在几天前在这个 reddit线程中回答了你的问题:

在Go中,地图不是线程安全的。 另外,如果例如可能有另一个正在写入相同数据的goroutine(同时也是这样),则数据还需要locking,即使读取也是如此。

根据你在评论中的澄清来看,也会有一些设置函数,你的问题的答案是肯定的,你将不得不用一个互斥体来保护你的读取; 你可以使用RWMutex 。 举个例子,你可以看看我写的(实际上是在reddit线程中链接的)一个表格数据结构的实现的来源 (在幕后使用一个映射)。

你可以使用并发映射来为你处理并发的痛苦。

 // Create a new map. map := cmap.NewConcurrentMap() // Add item to map, adds "bar" under key "foo" map.Add("foo", "bar") // Retrieve item from map. tmp, ok := map.Get("foo") // Checks if item exists if ok == true { // Map stores items as interface{}, hence we'll have to cast. bar := tmp.(string) } // Removes item under key "foo" map.Remove("foo") 

如果你只有一个作家,那么你可能会逃脱使用primefaces价值。 以下是从https://golang.org/pkg/sync/atomic/#example_Value_readMostly改编的(原来使用锁来保护写,所以支持多个作者);

 type Map map[string]string var m Value m.Store(make(Map)) read := func(key string) (val string) { // read from multiple go routines m1 := m.Load().(Map) return m1[key] } insert := func(key, val string) { // update from one go routine m1 := m.Load().(Map) // load current value of the data structure m2 := make(Map) // create a new map for k, v := range m1 { m2[k] = v // copy all data from the current object to the new one } m2[key] = val // do the update that we need (can delete/add/change) m.Store(m2) // atomically replace the current object with the new one // At this point all new readers start working with the new version. // The old version will be garbage collected once the existing readers // (if any) are done with it. }