预分配 unordered_map 的线程安全

Posted

技术标签:

【中文标题】预分配 unordered_map 的线程安全【英文标题】:Thread-safety of preallocated unordered_map 【发布时间】:2013-03-01 04:37:54 【问题描述】:

如果您确切知道无序映射将包含的最大元素数量,并且您预先分配了确切数量的存储桶。

哪些操作在该容器(不是存储在容器中的对象)上是线程安全的?

【问题讨论】:

通常 STL 容器对多个读取器是安全的,但对多个写入器却不是。 我认为(几乎)所有没有同时写入相同读取位置的读取都是安全的,就像其他容器一样。 所以预分配存储桶不会提供额外的线程安全级别? (我期待这可能是答案,但希望不是..) 确切的桶数?你真的认为如果哈希映射中有 100 个元素,那么映射正好使用 100 个桶吗? @Doug T,还有 Mark Garcia,您能为此参考一些规范/文档吗?您的 cmets 中有“通常”和“几乎”,实际上它总是代码中非典型且几乎从未发生过的分支,百万分之一爆炸:) 【参考方案1】:

从您的问题来看,您似乎并没有完全理解哈希映射又名 unordered_map 的工作原理。您可以阅读this article on wiki 以更好地理解它。所以如果你不是说 如果您拥有minimal perfect hash function,那么将桶的数量设置为与预期的元素数量完全相同会使事情变得更糟。如果您确实希望有最小的完美散列函数,这是一个非常特殊的情况,您应该提到这个问题,以及您将如何实现它。

无论如何,即使您提供最小的完美哈希函数,我也怀疑您是否会在 unordered_map 的操作上获得任何正式的线程安全保证。

【讨论】:

目的不是为了提高性能或完善散列,而是防止容器被重新散列,从而防止元素四处移动。 您应该阅读并理解那篇文章。为了使散列图均匀地分割 n 个桶中的 n 个对象,您必须具有最小的完美散列函数。否则,您将无法轻松预测您的 n 个对象将使用多少个存储桶,并且您的问题毫无意义 - 将存储桶数量设置为特定值不会影响线程安全。

以上是关于预分配 unordered_map 的线程安全的主要内容,如果未能解决你的问题,请参考以下文章

unordered_map 中的 C++ 线程(无复制构造函数)

std::unordered_map 上的线程安全包装器

不断迭代的线程安全的 Unordered_map

如何以线程安全的方式使用`std::unordered_map`?

如何在 C++ 中单独锁定 unordered_map 元素

如何终止线程池中的所有预分配线程?