Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/algorithm/11.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ Hashmap实现邻接列表_C++_Algorithm_Data Structures_Graph - Fatal编程技术网

C++ Hashmap实现邻接列表

C++ Hashmap实现邻接列表,c++,algorithm,data-structures,graph,C++,Algorithm,Data Structures,Graph,我已经使用向量向量方法实现了一个邻接列表,向量向量的第n个元素表示节点n的朋友列表 我想知道哈希映射数据结构是否更有用。我仍然犹豫不决,因为我根本无法识别它们之间的差异,例如,如果我想在第n个元素的邻域中检查并执行操作(搜索、删除),它怎么可能比向量的方法更有效。向量的向量 当不需要删除边时,向量向量是一个很好的解决方案 您可以在O(1)中添加边,也可以在O(N)中迭代邻居。 您可以通过vector[node]删除边。擦除(边)但速度较慢,复杂性仅为O(顶点数) 散列映射 我不确定您想如何使用哈

我已经使用向量向量方法实现了一个邻接列表,向量向量的第n个元素表示节点n的朋友列表

我想知道哈希映射数据结构是否更有用。我仍然犹豫不决,因为我根本无法识别它们之间的差异,例如,如果我想在第n个元素的邻域中检查并执行操作(搜索、删除),它怎么可能比向量的方法更有效。

向量的向量 当不需要删除边时,向量向量是一个很好的解决方案

您可以在O(1)中添加边,也可以在O(N)中迭代邻居。 您可以通过
vector[node]删除边。擦除(边)
但速度较慢,复杂性仅为O(顶点数)

散列映射 我不确定您想如何使用哈希映射。如果插入边意味着设置
hash\u map[edge]=1
,请注意,您无法迭代节点的邻居。

如果节点集是固定的,则
向量是一种很好的方法。然而,如果你突然决定删除一个节点,你会很恼火。不能收缩向量,因为它会置换节点后存储的元素,并且会丢失引用。另一方面,如果您保留了一个免费(可重用)ID列表,那么您只需“清空”插槽,然后在以后重用即可。效率很高

使用
无序的_映射
可以更轻松地删除节点。您可以继续为新创建的节点分配新ID,并且不会丢失空插槽。它不是那么紧凑,特别是在碰撞时,但也不是那么糟糕。当需要使用较旧的编译器移动向量时,重新灰化可能会有些慢

最后,无序的多重映射可能是最容易管理的映射之一。它也将记忆随风飘散,但嘿:)

就我个人而言,我会从一个无序的多重映射开始原型设计,只有当它对我的需求来说太慢时,我才会切换到另一个表示


注意:如果邻接关系是对称的,则可以通过建立比
(x,y)
仅存储
min(x,y)
的关系来减少一半的节点数。

向量向量向量如果需要删除节点,这是一个可怕的解决方案,因为最终会对部分节点重新编号,然后扫描所有边以修复节点编号。删除边很容易,只需在单个向量上使用“擦除-删除”习惯用法即可删除特定边。@AndréCaron:不一定。您可以简单地“清空”插槽,并在以后添加新节点时重新使用。@MatthieuM.:出于两个原因,我会避免这样做。首先,您将无法区分表示没有出站边的顶点的插槽和“空”插槽。第二,如果定期删除节点,最终将得到一个令人讨厌的稀疏数据结构。您的答案中描述的方法对于动态图结构更好。