* * 1959年Dijkstra发表了单源地最短路径算法【E. W. Dijkstra, “A Note on Two Problems in Connection with Graphs,” Numerische Mathematik, vol. 1, 269~271】,如果有向图上弧的权值为负数,则不能应用Dijkstra算法求解单源地最短路径问题, 而应用Bellman -Ford算法,请参见Bellman 发表的论文【R. Bellman,“On a Routing Problem,”Quarterly of Applied Mathematics,vol. 16, 87~90】。 * * 1. 问题提出 用带权的有向图表示一个交通运输网,图中: 顶点——表示城市 边——表示城市间的交通联系 权——表示此线路的长度或沿此线路运输所花费用等 问题:从某顶点出发,沿图的边到达另一顶点所经过的路径中,各边上权值之和最小的一条路径——最短路径 6.7 最短路径 2. 从某个源点(给定的)到其余各顶点的最短路径 5 1 6 4 3 2 0 8 5 6 2 30 13 7 17 32 9 13 长度 最短路径 V0,V1 V0,V2 V0,V2,V3 V0,V2,V3,V4 V0,V2,V3,V4,V5 V0,V1,V6 8 13 19 21 20 * * 3. Dijkstra算法的基本思想 按 路径长度递增顺序 求最短路径算法 。与求最小生成树的普里姆算法类似。 4. Dijkstra 算法的基本步骤 符号说明 利用带权邻接矩阵cost 表示当前找到的从源点V0到每个终点Vi的最短路径长度的辅助向量dist[i] 存储最短路径的向量path[i] 表示已找到从V0出发的最短路径的终点的集合S * * 算法步骤: 1. 用cost 初始化dist;置S={V0}; 2. 选择Vj,使得:dist[j]=Min{dist[i]|Vi∈V-S} Vj 就是当前求得的从V0出发的最短路径的终点,并将Vj并入S; 3. 对V-S上的所有顶点Vk,修改: dist[k]=Min{dist[j]+cost[j, k], dist[k]} 4. 重复2,3, n-1次。 * * 例如: * * 迪杰斯特拉算法的求解过程 * * * * 13 V0,V1 8 V0,V2 ? 30 V0,V4 ? 32 V0,V6 V2:8 V0,V2 13(V2) V0,V1 ------- 13 V0,V2,V3 30 V0,V4 ? 32 V0,V6 V1:13 V0,V1 (V1) ------- ------- 13 V0,V2,V3 30 V0,V4 22 V0,V1,V5 20 V0,V1,V6 V3:13 V0,V2,V3 (V3) ------- ------- ------- 19 V0,V2,V3,V4 22 V0,V1,V5 20 V0,V1,V6 V4:19 V0,V2,V3,V4 终点 从V0到各终点的最短路径及其长度 V1 V2 V3 V4 V5 V6 Vj (V4) -------- -------- -------- -------- 21 V0,V2,V3,V4,V5 20 V0,V1,V6 V6:20 V0, V1,V6 5 1 6 4 3 2 0 8 5 6 2 30 13 7 17 32 9 Min{v0-vi,v0-v2-vi} * * 5. 算法实现 图用带权邻接矩阵存储ad[][] 数组dist[]存放当前找到的从源点V0到每个终点的最短路径长度,其初态为图中直接路径权值 数组pre[]表示从V0到各终点的最短路径上,此顶点的前一顶点的序号;若从V0到某终点无路径,则用0作为其前一顶点的序号。 * * 6 2 7 5 4 3 1 8 5 6 2 30 13 7 17 32 9 dist 0 1 2 3 4 5 6 0 13 8 ? 30 ? 32 pre 0 1 2 3 4 5 6 0 1 1 0 1 0 1 (1) k=1 1 13 3 1 22 20 2 2 19 4 1 21 5 1 1 1 长度 最短路径 13 V1,V2 8 V1,V3 13 V1,V3,V4 19 V1,V3,V4,V5 21 V1,V3,V4,V5,V6 20 V1,V2,V7 算法分析:T(n)=O(n2) * * void shortpa
原创力文档

文档评论(0)