迭代 unordered_map C++

Posted

技术标签:

【中文标题】迭代 unordered_map C++【英文标题】:Iterating over unordered_map C++ 【发布时间】:2018-06-15 07:28:12 【问题描述】:

在 unordered_map 中以特定顺序插入的键是否会在使用迭代器迭代地图时以相同的顺序出现?

例如:如果我们在 B 中插入 (4,3), (2, 5), (6, 7)。 并像这样迭代:

for(auto it=B.begin();it!=B.end();it++) 
    cout<<(it->first); 

它会给我们 4、2、6 还是键可以按任何顺序出现?

【问题讨论】:

之所以称为“无序”,是因为插入元素的存储和迭代顺序通常不是客户端代码可以用于其自身目的的东西。如果您想按插入顺序排序,如果您不需要删除元素,最好使用vector,或者使用std::map 键入插入时间戳(具有足够的分辨率以保证唯一性)或递增插入计数器。 在当前的实现中,unordered_map 只是一个哈希图,因此不会保留插入顺序:***.com/questions/18414579/… 【参考方案1】:

来自cplusplus.com页面关于unordered_map(link)的begin成员函数:

请注意,unordered_map 对象不保证将哪个特定元素视为其第一个元素

所以不,不能保证元素会按照它们插入的顺序被迭代。

仅供参考,您可以更简单地迭代 unordered_map

for (auto& it: B) 
    // Do stuff
    cout << it.first;

【讨论】:

【参考方案2】:

信息添加到@Aimery提供的answer,

无序映射是一个关联容器,其中包含具有唯一键的键值对。搜索、插入和删除元素 具有平均恒定时间复杂度。

在内部,元素没有按任何特定顺序排序,而是组织成桶。元素放入哪个桶 完全取决于其密钥的散列。这允许快速访问 单个元素,因为一旦计算哈希,它指的是 元素放入的确切存储桶。

参见参考文献。来自https://en.cppreference.com/w/cpp/container/unordered_map。

根据Sumod Mathilakath在知乎给出了答案

如果您希望按排序顺序保留中间数据,请使用 std::map&lt;key,value&gt; 而不是 std::unordered_map。默认情况下,它将使用std::less&lt;&gt; 对键进行排序,因此您将按升序获得结果。

std::unordered_map是哈希表数据结构的实现,所以内部会根据std::unordered_map使用的哈希值对元素进行排列。但在std::map 的情况下,它通常是一个红黑二叉树实现。

参见参考文献。来自What will be order of key in unordered_map in c++ and why?。

所以,我认为我们得到了更清楚的答案。

【讨论】:

这并不能回答迭代顺序是否与插入顺序相同的问题 - 正如@Aimery 两年前指出的那样,情况并非如此

以上是关于迭代 unordered_map C++的主要内容,如果未能解决你的问题,请参考以下文章

unordered_map 迭代器指向 end(),如何从 unordered_map 中检索键?

unordered_map 迭代器会改变吗?

为啥我不能增加 std::unordered_map 迭代器?

为啥允许 std::unordered_map::rehash() 使迭代器无效?

迭代 unordered_map 的复杂性是啥

迭代 unordered_map C++