Go 多线程使用Map

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Go 多线程使用Map相关的知识,希望对你有一定的参考价值。

最近的项目中用到了GO自带的Map用于存储临时数据,且此Map只增加不删除,主要有两个线程会对其操作。临时数据结构如下

Var Map map[string]UsrStu
Lock

1:线程一周期性的遍历此Map,并有可能修改其值

2:线程二随机时间被调用,并向Map中增加数据

 因为涉及多线程,所以需要配合锁。对线程一和线程二的优先级进行讨论

 

情况一:如果线程二的优先级没有线程一高,那么处理方式如下:

线程一:

加锁
遍历处理
解锁

线程二:

加锁
添加元素
解锁

那么在Map元素数量较多时,就有可能在遍历过程中,线程二会出现阻塞。所以在线程二优先级较高时需要改进。对于线程一改进如下

线程一(错误的方式)
For k,v in Map   加锁   获取元素   解锁   对v处理
  加锁   Map[k]处理   解锁 End

 

这样便可以尽快处理线程二。但这样变没有考虑到线程一对Map的遍历是随机的一旦加入后,无法保证按原先的顺序继续执行。

这里需要对数据结构进行修改。

type  UserMapStu struct {
    KeyMap map[string]int
    DataSlice []didMdcStu
    sync.RWMutex
}
var UMap UserMapStu 

 线程一遍历时,不在对Map结构遍历,而是遍历DataSlice。

线程二加入数据时,首先判断是否存在,如果不存在,那么加入数据时,先将数据添加到Dataslice,返回下表,作为KeyMap的Value。而Key不变。

 

以上是关于Go 多线程使用Map的主要内容,如果未能解决你的问题,请参考以下文章

go sync.map的使用

map源码解析

Go 实现线程安全 map 读写(sync.RWMutex)

用go写爬虫服务并发请求,限制并发数

Go语言 sync.Map(在并发中使用)

多线程 Thread 线程同步 synchronized