Go中map默认不安全的,也实现了并发安全的对象:sync.Map
并发不安全
不安全是因为源码中没有实现读写分离。进行了判断异常:
在哈希表写操作时,会将哈希表的标志位
hashWriting
设置为 1,以表明当前正在执行写操作。当其他协程执行哈希表的读操作时,会根据当前的标志位判断是否能够执行读操作,如果标志位为hashWriting
,则说明当前正在执行写操作,就会抛出concurrent map read and map write
的异常,提示读写并发冲突。
if h.flags&hashWriting != 0 { fatal("concurrent map read and map write") }
sync.Map
要在并发环境下安全地使用哈希表,需要使用 Go 语言提供的并发安全的哈希表 sync.Map
。使用 sync.Map
可以避免在多个协程同时读写哈希表时发生并发冲突的问题。
sync.Map
中的读写操作是并发安全的,因为它内部实现了读写锁,能够保证并发读写时的线程安全。sync.Map
的读写操作与普通哈希表的操作基本相同,主要有以下几个方法:
Load(key interface{}) (value interface{}, ok bool)
:根据键获取值,并返回是否存在;Store(key, value interface{})
:根据键存储值;LoadOrStore(key, value interface{}) (actual interface{}, loaded bool)
:根据键获取值,如果不存在则存储给定的值;Delete(key interface{})
:删除给定键的值;Range(f func(key, value interface{}) bool)
:遍历哈希表,并将每个键值对传递给给定的函数 f。
// 创建一个 sync.Map 对象 var m sync.Map // 存储数据 m.Store("key1", "value1") m.Store("key2", "value1") // 加载数据 //if value, ok := m.Load("key1"); ok { // fmt.Println(value) //} m.Load("key2") // 删除数据 //m.Delete("key1") // 遍历哈希表 m.Range(func(key, value interface{}) bool { fmt.Println(key, value) return true }) //key1 value1 //key2 value1
标签:Map,key,sync,value,interface,哈希,Go,相关 From: https://www.cnblogs.com/coder2020/p/17335274.html