C++ 在无序映射中引用值安全吗

C++ 在无序映射中引用值安全吗,c++,C++,例如: #include <unordered_map> class A{}; std::unordered_map<unsigned int, A> map {{0,{}},{1, {}},{2, {}}}; int main() { A& a1 = map[1]; // some insert and remove operations ( key 1 never removed) // .... } #包括 A类{}; 无序映射{{0,{}

例如:

#include <unordered_map>

class A{};
std::unordered_map<unsigned int, A> map {{0,{}},{1, {}},{2, {}}};

int main() {
  A& a1 = map[1];
  // some insert and remove operations ( key 1 never removed)
  // ....
}
#包括
A类{};
无序映射{{0,{},{1,{},{2,{}};
int main(){
A&a1=map[1];
//一些插入和移除操作(图例1从未移除)
// ....
}
在多次插入操作后,仍然使用
a1
引用键为“1”的值是否安全

换句话说:
由于std::vector将在容量更改时移动元素,因此不能保证其元素的引用有效。这一事实是否也适用于无序地图

是的,它是安全的。根据标准:

22.2.7无序关联容器[无序需求]

插入件和插入件不得影响插入件的有效性 对容器元素的引用,但可能会使对的所有迭代器无效 集装箱。擦除成员只能使迭代器和 引用已擦除的元素,并保留 未擦除的元素

引用是安全的,但迭代器不是

可能是“不太权威”的来源,但更容易阅读:

对无序映射容器中元素的引用在中仍然有效 所有情况下,即使在重新洗牌之后

在大量的插入操作之后

如果你是说或者,那没关系

(强调矿山)

如果由于插入而发生重新灰化,则所有迭代器都将无效。否则迭代器不受影响引用不会失效。仅当新的元素数大于
max\u load\u factor()*bucket\u count()
时,才会进行重新灰化。如果插入成功,则在节点句柄中保存该元素时获得的指向该元素的指针和引用将无效,并且在提取该元素之前获得的指向该元素的指针和引用将变为有效。(从C++17开始)


即使
std::vector
在内存中的位置发生变化,对其元素的引用难道不安全吗?我猜它与@김선달 “对向量的引用”和“对向量中元素的引用”是不一样的。或者不是。显然我错了。看。@ravenisadesk哦,我打错了。我是说它的元素Shi Sam,我很好奇:实现如何真正保证这一点?如果我是一个哈希表,并且需要增长,那么可能需要将所有底层数组重新定位到不同的内存位置。有什么想法吗?无序容器通常是指针的哈希表,因此容器中的值不受重新映射的影响。因此,当我执行
some\u unordered\u map.insert(some\u key,some\u value)
,将
某个值
复制到某个数组X的某处,并且该数组将始终保留在最初分配的位置。指向该位置的指针设置在不同的数组Y中,这可能会随着时间的推移调整大小和位置。当我执行
some\u unordered\u map.find(some\u key)
时,将在数组Y上执行查找,并将始终返回指向数组X中相同位置的指针。这就是为什么保留此指针(或引用)是有效的。我大致正确吗?没有什么要求将
某些值
复制到
数组
。在散列容器的常见实现中,容器中的值保存在单个链表中,数组桶用作散列桶;非常类似于
std::vector
。在任何情况下,
unordered\u map
都是一个模板。也就是说,在它的头文件中,你会发现100%的C++编译器的代码:如果您有兴趣了解它是如何工作的,您可以自己从编译器的头中读取它。