迪杰斯特拉 (Dijkstra) 算法
基本思想
- 通过 Dijkstra 计算图 G 中的最短路径时,需要指定一个起点 D (即从顶点 D 开始计算)。
- 此外,引进两个数组 S 和 U。S 的作用是记录已求出最短路径的顶点 (以及相应的最短路径长度),而 U 则是记录还未求出最短路径的顶点 (以及该顶点到起点 D 的距离)。
- 初始时,数组 S 中只有起点 D;数组 U 中是除起点 D 之外的顶点,并且数组 U 中记录各顶点到起点 D 的距离。如果顶点与起点 D 不相邻,距离为无穷大。
- 然后,从数组 U 中找出路径最短的顶点 K,并将其加入到数组 S 中;同时,从数组 U 中移除顶点 K。接着,更新数组 U 中的各顶点到起点 D 的距离。
- 重复第 4 步操作,直到遍历完所有顶点。
算法图解
以上图为例,来对迪杰斯特拉进行算法演示 (以顶点 D 为起点)。
初始状态:S 是已计算出最短路径的顶点集合,U 是未计算除最短路径的顶点的集合!
第 1 步:将顶点 D 加入到 S 中。
此时,S={D (0)}, U={A (∞),B (∞),C (3),E (4),F (∞),G (∞)}。 注:C (3) 表示 C 到起点 D 的距离是 3。
第 2 步:将顶点 C 加入到 S 中。
上一步操作之后,U 中顶点 C 到起点 D 的距离最短;因此,将 C 加入到 S 中,同时更新 U 中顶点的距离。以顶点 F 为例,之前 F 到 D 的距离为∞;但是将 C 加入到 S 之后,F 到 D 的距离为 9=(F,C)+(C,D)。
此时,S={D (0),C (3)}, U={A (∞),B (13),E (4),F (9),G (∞)}。
第 3 步:将顶点 E 加入到 S 中。
上一步操作之后,U 中顶点 E 到起点 D 的距离最短;因此,将 E 加入到 S 中,同时更新 U 中顶点的距离。还是以顶点 F 为例,之前 F 到 D 的距离为 9;但是将 E 加入到 S 之后,F 到 D 的距离为 6=(F,E)+(E,D)。
此时,S={D (0),C (3),E (4)}, U={A (∞),B (13),F (6),G (12)}。
第 4 步:将顶点 F 加入到 S 中。
此时,S={D (0),C (3),E (4),F (6)}, U={A (22),B (13),G (12)}。
第 5 步:将顶点 G 加入到 S 中。
此时,S={D (0),C (3),E (4),F (6),G (12)}, U={A (22),B (13)}。
第 6 步:将顶点 B 加入到 S 中。
此时,S={D (0),C (3),E (4),F (6),G (12),B (13)}, U={A (22)}。
第 7 步:将顶点 A 加入到 S 中。
此时,S={D (0),C (3),E (4),F (6),G (12),B (13),A (22)}。
此时,起点 D 到各个顶点的最短距离就计算出来了:A (22) B (13) C (3) D (0) E (4) F (6) G (12)。
代码实现
依据上述步骤思想进行实现即可,visited 数组表示已加入的顶点。
import java.util.*; |
预览: