1. 程式人生 > 其它 >圖的計算(2):帶權圖的最短路徑

圖的計算(2):帶權圖的最短路徑

技術標籤:圖論抽象代數幾何學

帶權圖(weighted digraph)

G=(V,E)是一簡單圖。稱一元函式 w:E®R+ 為圖G 的權函式,使得 對於每一條邊eÎE均有一正實數w(e)ÎR+與之對應,稱圖G帶有權w圖,簡稱為帶權圖。記為G=(V,E, w)。

最短路(shortest path)

G=(V,E,w)是一帶權圖

(1)設P=(ei1, ei2,¼, eik)G中的一條路。則路P的路長

定義為: w(P)=

 (2)從結點u到結點v的最短路P0滿足下述條件的路:

w(P0)=min{w(P) ê

Puv} 。

帶權圖中各邊的權值都為1時,則路長的定義就蛻化為§3一般圖的路長定義了。

E.W.Dijkstra演算法(1959):

 演算法的目標是求出帶權圖G中從結點v0到結點vn的最短路。

w 基本思想: 最短路上的任何一段(區域性)也都是最短的。即,如果 P 0 =( v 0 , v 1 , v 2 , ¼ , v n ) 是一條最短路,則其中任一段 ( v i , v i+1 , v i+2 , ¼ , v j ) (0 £ i < j £ n) 也是最短的。  

 特別地,最短路

P0 的任一真字首(v0, v1, v2,¼, vk)(k< n)也是最短的。

否則,將區域性段換為最短的,則可得一比P0更短的路P0¢這與已知P0是最短路矛盾。

     No1.P:={v0} ; T :=V\{v0} ;              /*設定P-T介面*/ 
            d(v0) :=0;(tT)(d(t) := ) ;
                                  /*做圓標號(用一重for迴圈可實現) */
            p := v0 ; mark(v0) := d(v0) ;           /*做方標號*/
     No2. (tT)(d(t) := min{d(t) , d(p)+w(p,t)}) ;
             /*按離介面最近方向修改圓標 號(用一重for迴圈可實現)*/
              (t0T)(tT)(d(t0) d(t)) ;
            /*尋求T 中圓標號最小的結點t0   (用一重for迴圈及if比較可實現)*/
     No3.P:=P{t0} ; T :=T\{t0} ;       /*修改P-T介面*/
              p := t0 ; mark(t0) := d(t0) ;        /*改圓為方*/
     No4.if t0 = vn  then  goto  exit ;
                            else goto No2 ;
Dijkstra 演算法的工作原理:

將帶權圖G的結點集V分成兩部分:一部分稱為具有P標號(方標號)的集合;另一部分稱為具有T標號(圓標號)的集合。所謂結點viP標號是指從v0vi的最短路的路長;而結點viT標號是指從v0vi的某條路徑的長度。

 Dijkstra演算法首先將v0取為 P 標號結點;其餘的結點均取為T標號結點;然後按離P-T介面最近方向逐步地將具有T標號的結點改為P標號結點。當結點vn也被改為P標號結點時,也就求出了從(起始)結點v0到各個結點vi的最短路長;尤其是求出了從(起始)結點v0到(終結)結點vn的最短路長。

程式計演算法:
   1.    P={v0};T={v1,v2,v3,v4,v5};       
          d(v0)=0; d(v1)=d(v2)=d(v3)=d(v4)=d(v5)=; p=v0; 
   2.    d(v1)=1 ; d(v2)=4 ; d(v3)=d(v4)=d(v5)=;
          t0 =v1;
   3.    P={v0,v1}; T={v2, v3,v4,v5}; p=v1; 
   4.    t0v5; go to  2;
   2.    d(v2)=3 ; d(v3)=8 ; d(v4)=6 ; d(v5)=  ; 
          t0=v2 ;
   3.    P={v0,v1,v2}; T={v3,v4,v5}; p=v2; 
   4.    t0 v5 ; go to 2 ;
   2.    d(v3)=8 ; d(v4)=4 ; d(v5)=  ;
          t0 = v4 ;
   3.    P={v0,v1,v2, v4};T={v3, v5}; p=v4;
   4.      t0 v5 ; go to 2;
   2. 	d(v3)=7; d(v5)=10;
    	 t0= v3;
   3. 	 P={v0, v1, v2, v4, v3}; T={v5} ; p=v3; 
   4. 	 t0v5 ; go to 2;
   2. 	 d(v5)=9;
    	 t0=v5 ;
   3. 	 P={v0,v1,v2,v4,v3,v5} ; T={ }; p=v5; 
   4.    t0=v5 ;exit ;
 

·顯然,上作業法的優點是直觀,缺點是畫圖麻煩 可以將No2步和No3步的圖合為一個圖,以達簡化的目地(例如圖3和圖4可合併成一個圖);

·顯然,程式計算法的優點是簡便、機械,缺點是缺乏直觀性、計算出錯不易檢查

Dijkstra 演算法的效果:

·Dijkstra演算法能夠一次性的求出從起點v0到帶權圖G中其餘每一個結點的最短路長(就是各結點方標號中的數值)。

·Dijkstra演算法沒有直接給出從起點v0到帶權圖G中其餘各結點的最短路。因此,要直接給出從起點v0到帶權圖G中其餘各結點的最短路,需要修改Dijkstra演算法,或者給其嵌入記憶系統(用表結構或僅記前一個結點)或者給其增加回溯功能。

Dijkstra演算法的特點

·Dijkstra演算法是沿著P-T介面(按離介面最近方向)向前推進的;而不是沿著最短路向前推進的。

Dijkstra 演算法的計算工作量:

  Dijkstra演算法的計算工作量主要是集中在No2。úPê=k , úTê=n-k(0£k £ n-1)P增加一個結點,需進入一次迴圈:

從表1可得Dijkstra演算法的(時間)複雜性是n2級的; (空間)複雜性也是n2級的。

加法(次)

比較(次)

存貯量(單元)

算一個結點

1

1

1

算一次迴圈

n-k-1

2(n-k-1)

1

完成計算

\frac{1}{2}n(n-1)

n(n-1)

n^{2}+2n+1