提问人:dw218192 提问时间:2/16/2022 更新时间:2/18/2022 访问量:796
为什么可以修改 Dijkstra 算法以找到 K 条最短路径?
Why can Dijkstra's Algorithm be modified to find K shortest paths?
问:
我试图找到一个直观的解释,解释为什么我们可以推广 Dijkstra 算法,以在没有负边的有向加权图中从单个源中找到 K 条最短(简单)路径。根据维基百科,修改后的 Dijkstra 的伪代码如下:
Definitions:
G(V, E): weighted directed graph, with set of vertices V and set of directed edges E,
w(u, v): cost of directed edge from node u to node v (costs are non-negative).
Links that do not satisfy constraints on the shortest path are removed from the graph
s: the source node
t: the destination node
K: the number of shortest paths to find
P[u]: a path from s to u
B: a heap data structure containing paths
P: set of shortest paths from s to t
count[u]: number of shortest paths found to node u
Algorithm:
P = empty
for all u in V:
count[u] = 0
insert path P[s] = {s} into B with cost 0
while B is not empty:
let P[u] be the shortest cost path in B with cost C
remove P[u] from B
count[u] = count[u] + 1
if count[u] <= K then:
for each vertex v adjacent to u:
let P[v] be a new path with cost C + w(u, v) formed by concatenating edge (u, v) to path P[u]
insert P[v] into B
return P
我知道,对于原始的 Dijkstra 算法,可以通过归纳法证明,当一个节点被添加到封闭集(或者如果它以 BFS + 堆的形式实现,则从堆中弹出)时,该节点的成本必须从源头开始最小。
这里的算法似乎基于这样一个事实,即当一个节点从堆中弹出第 i 次时,我们从源中获得第 i 个最小的成本。为什么会这样?
答:
2赞
kcsquared
2/18/2022
#1
Wiki 文章没有具体说明,但该代码只能解决 k-shortest-paths 的“循环”版本,其中路径不需要简单。
这个问题的简单路径版本更难:你需要看看像 Yen 算法这样的东西,它做聪明的过滤以避免在生成路径时重复点。Yen 的算法可以使用 Dijkstra 的算法作为子程序,但也可以使用任何其他最短路径算法来代替。
没有明显的方法可以修改 Dijkstra 的算法来解决 k-shortest-simple-paths 问题。您需要跟踪优先级队列中的路径(这已经在您发布的代码中完成),但每个顶点的浏览次数有一个指数上限。
在这里,对可以探索顶点的次数设置上限,这适用于非简单路径情况。另一方面,在最坏的情况下,直接修改 Dijkstra 的简单路径算法将需要您为之前访问过的节点的每个可能性(或可能稍微小一点的指数)探索一次节点。if count[u] <= K
K+1
2^(V-1)
评论