最短路径--标号法
本文介绍了一种常用的求最短路径的方法,很经典的.任何一本数据结构的教材上都能找到.至于算法的名称到不一定是"标号法",这个名称是从吴文虎的书上看来的.在比较通用的清华的绿皮书上到没提名称,只说了是个叫Dijistra(可能拼错了)的发明的(跟最小生成树的是不是同一个人呀,呵呵). 该算法是个不用搜索的高效的算法,但只能算出最短路径的长度,而没有记录最短路径.本文对该算法做了一点改进,弥补了这个缺陷. 先看看原算法是个什么样子的. 问题描述:给定简单无向图G,指定一顶点Vi为起点,对于任一Vj∈G且i≠j,求Vi到Vj的最短路径的长度. 换成实际运用中的大白话就这样说:"北京的小汤山医院已经投入使用了,在抗击非典的战役中发挥了重要的作用.现在,在北京市内有若干家收治非典病人的医院.各个医院之间的路程和各医院到小汤山之间的路程已知(有可能没有直通道路),由于非典病人的特殊性,在往小汤山转运的过程中只能在收治病人的医院中转.现在,党和政府交给了你一个光荣而艰巨的任务,计算出小汤山到市内各收治医院的最短路径,为抗非事业做出你应有的贡献." 算法分析: 1.初始化:起点的最短路径为0,其他顶点的最短路径为∞.所有顶点未标号. 2.在所有未标号的顶点中找出最短路径最短的顶点i.若无法找到,则说明所有顶点已标号,或者所有的未标号顶点都是无法到达的.转5 3.更改所有与i直接相邻的未标号顶点的最短路径.更新方法如下: 如果i的最短路径+边i,j的长度<j目前的最短路径,则j的最短路径更新为i的最短路径+边i,j的长度,否则不变. 也就是意味着通过i走向j比原来的方向走向j能获得更短的路径. 4.转2 5.输出结果 实例: 起点1 12 顶点2 未标号 -------------- 未标号 距离:0 距离:∞ | | | | 4| 6| | | 顶点3 5 顶点4 未标号 --------------- 未标号 距离:∞ 距离:∞ 找所有未标号中距离最短的顶点为起点1,将1做标号,更新于1相邻的2和3的距离 起点1 12 顶点2 已标号 -------------- 未标号 距离:0 距离:12 | | | | 4| 6| | | 顶点3 5 顶点4 未标号 --------------- 未标号 距离:4 距离:∞ 找所有未标号中距离最短的顶点为起点3,将3做标号,更新于1相邻的4的距离 起点1 12 顶点2 已标号 -------------- 未标号 距离:0 距离:12 | | | | 4| 6| | | 顶点3 5 顶点4 已标号 --------------- 未标号 距离:4 距离:9 找所有未标号中距离最短的顶点为起点4,将4做标号,更新于1相邻的2的距离(因为距离4+边2,4的长度>距离2,所以不更新) 起点1 12 顶点2 已标号 -------------- 未标号 距离:0 距离:12 | | | | 4| 6| | | 顶点3 5 顶点4 已标号 --------------- 已标号 距离:4 距离:9 找所有未标号中距离最短的顶点为起点2,将2做标号,已没有与2相邻的未标号顶点需要更新了. 起点1 12 顶点2 已标号 -------------- 已标号 距离:0 距离:12 | | | | 4| 6| | | 顶点3 5 顶点4 已标号 --------------- 已标号 距离:4 距离:9 再次找所有未标号中距离最短的顶点已找不到,得结果为d(2)=12, d(3)=4, d(4)=9.