floyd算法

    最近开始学算法,感觉存在电脑总有些不安全,没办法,这不是自己的电脑。

    对于最短路径算法,floyd的算法的代码无疑是最容易写出来的,代码量少,而且很简洁。

    首先要明确floyd算法的思想:从Vi到Vj的所有可能存在的路径中,选出一条长度最短的路径。

    若<vi,vj>存在,则存在路径{vi,vj}。// 路径中不含其它顶点

    若<vi,v1>,<v1,vj>存在,则存在路径{vi,v1,vj}。// 路径中所含顶点序号不大于1

    若{vi, …, v2}, {v2, …, vj}存在,则存在一条路径{vi, …, v2, …, vj}。 // 路径中所含顶点序号不大于2

     …

    依次类推,则 vi 至 vj 的最短路径应是上述这些路径中,路径长度最小者。

 

    下为简单的测试图,有点难看,蛋定蛋定,代码中有解释

    

   

 

 

 1 #include<iostream>
 2 using namespace std;
 3 
 4 const int MAXNUM=101;
 5 
 6 int MAP[MAXNUM][MAXNUM]={
 7     {INT_MAX,      2,INT_MAX,INT_MAX,INT_MAX,      9,     15,INT_MAX,INT_MAX},
 8     {INT_MAX,INT_MAX,      4,INT_MAX,INT_MAX,INT_MAX,      6,INT_MAX,INT_MAX},
 9     {INT_MAX,INT_MAX,INT_MAX,      2,INT_MAX,INT_MAX,INT_MAX,INT_MAX,     15},
10     {INT_MAX,INT_MAX,INT_MAX,INT_MAX,      1,INT_MAX,INT_MAX,INT_MAX,      1},
11     {INT_MAX,INT_MAX,INT_MAX,INT_MAX,INT_MAX,      6,INT_MAX,      3,INT_MAX},
12     {INT_MAX,INT_MAX,INT_MAX,INT_MAX,INT_MAX,INT_MAX,INT_MAX,     11,INT_MAX},
13     {INT_MAX,INT_MAX,INT_MAX,INT_MAX,INT_MAX,INT_MAX,INT_MAX,     15,      2},
14     {INT_MAX,INT_MAX,INT_MAX,INT_MAX,INT_MAX,INT_MAX,INT_MAX,INT_MAX,      4},
15     {INT_MAX,INT_MAX,INT_MAX,INT_MAX,INT_MAX,INT_MAX,INT_MAX,INT_MAX,INT_MAX}
16 };
17 
18 int dist[MAXNUM][MAXNUM];    //记录i到j的最短路径
19 int path[MAXNUM][MAXNUM];    //记录i到j路径中倒数第二个顶点        
20 
21 #define MAXSUM(a,b) ( ((a)!=INT_MAX&&(b)!=INT_MAX) ? ((a)+(b)) : INT_MAX )
22 
23 void floyd(int n)
24 {
25     int i,j,k;
26     for(i=0;i<n;++i)    //初始化dist数组,path数组
27         for(j=0;j<n;++j)
28         {
29             dist[i][j]=MAP[i][j];
30             //path的值初始化为i,既i到j的倒数第二个顶点为i
31             path[i][j]=i;    
32         }
33 
34     //将所有的顶点插到i到j的路径中,既(i,k)(k,j)
35     for(k=0;k<n;++k)    
36         for(i=0;i<n;++i)
37             for(j=0;j<n;++j)
38                 if(dist[i][j]>MAXSUM(dist[i][k],dist[k][j]))
39                 {
40                     //dist[i][j]=min{dist[i][j],dist[i][k]+dist[k][j]}
41                     dist[i][j]=MAXSUM(dist[i][k],dist[k][j]);    
42                     //确定i到j的路径经过k,则路径中倒数第二个顶点就要更新
43                     path[i][j]=path[k][j];    
44                 }
45 }
46 
47 void reverse(int a[],int n)
48 {
49     for(int i=0,j=n-1;i<j;++i,--j)
50         swap(a[i],a[j]);
51 }
52 
53 int getpath(int a[],int i,int j)
54 {
55     int count=1,k=j;
56     a[0]=j;
57     while(i!=k)
58     {
59         //path记录的是i到k的路径中k的前一个顶点,故依次回溯
60         k=a[count++]=path[i][k];    
61     }
62     reverse(a,count);
63     return count;
64 }
65 
66 int main()
67 {
68     floyd(9);
69     int a[MAXNUM];
70     for(int i=0;i<9;++i)
71         for(int j=0;j<9;++j)
72             if(dist[i][j]!=INT_MAX)
73             {
74                 cout<<char(i+'a')<<""<<char(j+'a')<<"的最短路径为:";
75                 cout<<dist[i][j]<<endl;
76                 int length=getpath(a,i,j);
77                 for(int k=0;k<length;++k)
78                     cout<<char(a[k]+'a')<<' ';
79                 cout<<endl<<endl;
80             }
81     return 0;
82 }

 

posted on 2011-01-31 23:21  bug睡的略爽  阅读(195)  评论(0编辑  收藏  举报

导航