我有一个std :: map(或者std :: unordered_map,因为我认为它们的行为类似)我读写的内容。我也有一个相关的互斥锁。
我将同时阅读和写入(通过插入或删除元素)到地图。我听说STL容器是安全的。如果是这样,只使用互斥锁进行写操作是安全的吗?
我问,因为我需要在某一点迭代地图的值,并且我只想在元素需要修改时才使用我的互斥锁。
答案 0 :(得分:1)
只使用互斥锁进行写操作是安全的吗?
您需要确保在写入地图时不要尝试从地图中读取数据。所以你不需要在只读取时锁定互斥锁,但如果任何线程可能正在编写,那么所有线程(甚至读者)都需要使用互斥锁。
答案 1 :(得分:0)
一般来说,没有。读者和作者都必须获得互斥锁。
否则,当存在并发读取和写入时,您将面临数据争用的风险,从而导致未定义的行为。在实践中,可能导致崩溃,或者读者可能会获得您从未放入地图的损坏数据。即使如果它似乎有效,它也会混淆有用的工具,比如种族探测器(例如,thread sanitizer,Helgrind)。它还使您的代码可能不可移植。
只有当您能够证明地图上没有更多的编写者,并且所有其他线程都可以看到更改时,情况就会发生变化,因为现在所有访问都是读者。此时,不会有任何数据争用,并且可以安全地从地图中读取而不进行任何同步。
如果仍有更新的可能性,您可以使用并行数据结构来避免锁定。 C ++ 11(和C ++ 17)没有提供,但有非标准的实现可用。
因此,如果您确实需要性能,可以查看这些并发哈希映射实现(否则只需将std::unordered_map
与互斥锁结合使用):
std::unorder_map
,但不支持并发删除操作)