赞
踩
相关blog:【图】最短路径Dijkstra算法C语言实现
1.把图用邻接矩阵G表示出来,如果从Vi到Vj有路可达,则 G [ i ] [ j ] = d G[i][j]=d G[i][j]=d, d d d表示该路的长度;否则 G [ i ] [ j ] = ∞ G[i][j]=∞ G[i][j]=∞。一个点到自己的距离如 G [ i ] [ i ] = 0 G[i][i]=0 G[i][i]=0
2.定义一个矩阵D用来记录所插入点的信息,
D
[
i
]
[
j
]
D[i][j]
D[i][j]表示从
V
i
Vi
Vi到
V
j
Vj
Vj需要经过的点,初始化
D
[
i
]
[
j
]
=
−
1
D[i][j]=-1
D[i][j]=−1。
3.把各个顶点插入图中,比较插点后的距离与原来的距离,
G
[
i
]
[
j
]
=
m
i
n
(
G
[
i
]
[
j
]
,
G
[
i
]
[
k
]
+
G
[
k
]
[
j
]
)
G[i][j] = min( G[i][j], G[i][k]+G[k][j] )
G[i][j]=min(G[i][j],G[i][k]+G[k][j]),如果
G
[
i
]
[
j
]
G[i][j]
G[i][j]的值变小,则
D
[
i
]
[
j
]
=
k
D[i][j]=k
D[i][j]=k(记录中间结点)。在
G
G
G中包含有两点之间最短道路的信息,而在
D
D
D中则包含了最短通路径的信息。
比如,要寻找从V5到V1的路径。根据D,假如 D ( 5 , 1 ) = 3 D(5,1)=3 D(5,1)=3则说明从V5到V1经过V3,路径为 V 5 , V 3 , V 1 {V5,V3,V1} V5,V3,V1,如果 D ( 5 , 3 ) = 3 D(5,3)=3 D(5,3)=3,说明V5与V3直接相连,如果 D ( 3 , 1 ) = 1 D(3,1)=1 D(3,1)=1,说明V3与V1直接相连。
4. D D D即为所有点对的最短路径矩阵
5.得到最短路径矩阵后,若 p a t h [ i ] [ j ] = − 1 path[i][j]=-1 path[i][j]=−1,表示此路通,可以直接输出,否则, i , j i,j i,j不直接相通,第一个中间结点 m i d = p a t h [ i ] [ j ] mid=path[i][j] mid=path[i][j],继续将 p a t h [ i ] [ m i d ] path[i][mid] path[i][mid]和 p a t h [ m i d ] [ j ] path[mid][j] path[mid][j]递归求解.
#include<stdio.h> #define SIZE 110 #define INF 1000000 int sum=0; void Floyd(int n,int Graph[][SIZE],int path[][SIZE])//求最短路径矩阵path[][] { int i,j,k; int A[SIZE][SIZE]; for(i = 0;i < n;i++) { for(j = 0;j < n;j++) { A[i][j] = Graph[i][j]; path[i][j] = -1; } } for(k = 0;k < n;k++) { for(i=0;i < n;i++) { for(j=0;j < n;j++) { if(A[i][j]>A[i][k]+A[k][j]) { A[i][j] = A[i][k]+A[k][j]; path[i][j] = k; } } } } } int gen(int map[SIZE][SIZE],int start ,int end)//图的建立 { int vertex; int i,j; int k; int Ver; int edge_num; scanf("%d%d",&vertex,&edge_num); for(i=0;i<=vertex;i++) { for(j=0;j<=vertex;j++) if(i == j) { map[i][j] = 0; } else { map[i][j] = INF; } } for(k=0;k<edge_num;k++) { scanf("%d%d",&i,&j); scanf("%d",&map[i][j]); //map[j][i]=map[i][j]; } return vertex;//返回顶点数目 } void shortpath(int start,int end,int path[][SIZE],int Graph[][SIZE])//打印最短路径 { if(path[start][end] == -1) { printf("<%d,%d>",start,end); sum = sum+Graph[start][end]; } else { int mid = path[start][end]; shortpath(start,mid,path,Graph); shortpath(mid,end,path,Graph); } } int main () { int Graph[SIZE][SIZE]; int path[SIZE][SIZE]; int start,end; scanf("%d%d",&start,&end);//记录出发点和目的地 int vertexnum = gen(Graph,start,end); Floyd(vertexnum,Graph,path); shortpath(start,end,path,Graph); printf("\n%d",sum); return 0; }
输入:
1 0//从1到0的最短路径
4 8//四个顶点八条边
0 1 5
0 3 7
1 2 4
1 3 2
2 0 3
2 1 3
2 3 2
3 2 1
输入的后8行相当于
map[0][1] = 5; //测试数据
map[0][3] = 7;
map[1][2] = 4;
map[1][3] = 2;
map[2][0] = 3;
map[2][1] = 3;
map[2][3] = 2;
map[3][2] = 1;
输出:
<1,3><3,2><2,0>//轨迹
6 //最短路径
相关blog:【图】最短路径Dijkstra算法C语言实现
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。