我正在尝试实现一种算法,用于在存储为邻接表的无向图中找到欧拉路径。我需要一种快速的方法(线性时间)从图形中删除一条边。
我最初的想法是使用
vector<list<pair<Vertex, List<Vertex>::iterator>>> Graph
因此,当我沿一个方向删除边缘时,我将有一种快速的方法,即使用迭代器将其沿相反的方向删除,将其存储在相反的方向上。但是,一些消息来源声称这些迭代器将不再有效,因为当我开始删除项目时,指针结构将变得不同,并且这些迭代器将不再指向正确的元素。
我的问题是,有没有一种方法可以使用邻接表在O(1)时间内删除边,还是有办法以某种方式标记边,所以当我位于相邻顶点时,我肯定会知道沿相反方向的边缘被遍历。预先感谢。
答案 0 :(得分:1)
我需要一种快速的方法(线性时间)从图形中删除一条边。
有可能,但是由于所描述的问题,您必须更改图形表示。
方法1 -确保O(logE)复杂性
只需使用std::set
而不是std::list
:
std::vector<std::set<int>> Graph;
这允许以相同方式遍历和处理所有相邻节点:
// adj is your graph,
// v is current vertex
for (auto &w : adj[v]) {
// process edge [v, w]
}
但是您可以在O(logE)中custom validaotor相对边缘:
// remove [v,w] and [w,v]
adj[v].erase(w);
adj[w].erase(v);
方法2 -平均O(1),最差情况O(E)
std :: unordered_set可以实现恒定的时间复杂度,但只能平均:
std::vector<std::unordered_set<int>> Graph;
整理和擦除模式保持不变,但就我个人而言,我更喜欢方法1。