C語言弗洛伊德演算法的實現
阿新 • • 發佈:2019-01-07
弗洛伊德演算法和迪傑斯特拉演算法一樣,用於求兩個節點之間的最短路徑,過程也比迪傑斯特拉演算法更為簡單。以下是實現程式碼:
首先仍然是預定義和型別定義:
#define OK 1 #define ERROR 0 #define Max_Int 37262 #define MVNum 100 typedef int Status; typedef char VerTexType; typedef int ArcType; typedef struct{ VerTexType vex[MVNum]; ArcType arc[MVNum][MVNum]; int vexnum, arcnum; }AMGraph;
並定義兩個二維陣列:
int Path[MVNum][MVNum];
ArcType D[MVNum][MVNum];
建立有向圖:
int LocateVex(AMGraph *G, VerTexType v) { int i; for (i = 0; i < G->vexnum; i++) { if (G->vex[i] == v) return i; } return -1; } Status CreateUDN(AMGraph *G) { VerTexType v1, v2; ArcType w; int i, j, k; printf("輸入總節點數、總邊數:"); scanf("%d %d", &G->vexnum, &G->arcnum); printf("輸入節點的值:"); fflush(stdin); for (i = 0; i < G->vexnum; i++) { scanf("%c", &G->vex[i]); } for (i = 0; i < G->vexnum; i++) for (j = 0; j < G->vexnum; j++) { G->arc[i][j] = Max_Int; } for (k = 0; k < G->arcnum; k++) { fflush(stdin); printf("依次輸入邊的兩個頂點以及邊的權值:"); scanf("%c %c %d", &v1, &v2, &w); i = LocateVex(G, v1); j = LocateVex(G, v2); G->arc[i][j] = w; } return OK; }
弗洛伊德演算法:
void ShortestPath_Floyd(AMGraph G) { int i, j, k; for (i = 0; i < G.vexnum;i++) for (j = 0; j < G.vexnum; j++) { D[i][j] = G.arc[i][j]; if (D[i][j] < Max_Int) Path[i][j] = i; else Path[i][j] = -1; } for (k = 0; k < G.vexnum;k++) for (i = 0; i < G.vexnum;i++) for (j = 0; j < G.vexnum; j++) { if (D[i][j]>D[i][k] + D[k][j]) { D[i][j] = D[i][k] + D[k][j]; Path[i][j] = Path[k][j]; } } }
初始化:將D[i][j]賦值為i,j邊的權值,並判斷其權值若不為最大值(Max_Int),則將Path[i][j]賦值為0,否則賦值為-1.
依次判斷i,j下標的邊的權值是否大於i、k和k、j下標邊的權值之和,若大於,則說明目前記錄的並非最短路徑,將i、k和k、j下標邊的權值之和賦值給D[i][k],並將Path[k][j]賦值給Path[i][j]。
加入main():
int main(void)
{
int i, j;
AMGraph G;
CreateUDN(&G);
ShortestPath_Floyd(G);
for (i = 1; i < G.vexnum; i++)
{
if (D[0][i] == Max_Int)
printf("0無法到達%c\n", G.vex[i]);
else
printf("0到%c的權值為:%d\n", G.vex[i], D[0][i]);
}
return 0;
}