• Floyd算法简单实现(C++)


    图的最短路径问题主要包括三种算法:

    (1)Dijkstra (没有负权边的单源最短路径)

    (2)Floyed (多源最短路径)

    (3)Bellman (含有负权边的单源最短路径)

    本文主要讲使用C++实现简单的Floyd算法,Floyd算法原理参见 Floyd–Warshall algorithm

    Floyd算法简单实现(C++)

      1 #include<iostream>
      2 using namespace std;
      3 
      4 #define MAXVEX 10
      5 #define INFINITY 65535
      6 
      7 typedef int Patharc[MAXVEX][MAXVEX];
      8 typedef int ShortPathTable[MAXVEX][MAXVEX];
      9 
     10 typedef struct {
     11     int vex[MAXVEX];
     12     int arc[MAXVEX][MAXVEX];
     13     int numVertexes;
     14 } MGraph;
     15 
     16 // 构建图
     17 void CreateMGraph(MGraph *G){
     18     int i, j, k;
     19 
     20     // 初始化图
     21     G->numVertexes = 9;
     22     for(i = 0; i < G->numVertexes; ++i){
     23         G->vex[i] = i;
     24     }
     25     for(i = 0; i < G->numVertexes; ++i){
     26         for(j = 0; j < G->numVertexes; ++j){
     27             if(i == j)
     28                 G->arc[i][j] = 0;
     29             else
     30                 G->arc[i][j] = G->arc[j][i] = INFINITY;
     31         }
     32     }
     33 
     34     G->arc[0][1] = 1;
     35     G->arc[0][2] = 5;
     36 
     37     G->arc[1][2] = 3;
     38     G->arc[1][3] = 7;
     39     G->arc[1][4] = 5;
     40 
     41     G->arc[2][4] = 1;
     42     G->arc[2][5] = 7;
     43 
     44     G->arc[3][4] = 2;
     45     G->arc[3][6] = 3;
     46 
     47     G->arc[4][5] = 3;
     48     G->arc[4][6] = 6;
     49     G->arc[4][7] = 9;
     50 
     51     G->arc[5][7] = 5;
     52 
     53     G->arc[6][7] = 2;
     54     G->arc[6][8] = 7;
     55 
     56     G->arc[7][8] = 4;
     57 
     58     // 设置对称位置元素值
     59     for(i = 0; i < G->numVertexes; ++i){
     60         for(j = i; j < G->numVertexes; ++j){
     61             G->arc[j][i] = G->arc[i][j];
     62         }
     63     }
     64 }
     65 
     66 // Floyd algorithm
     67 void ShortPath_Floyd(MGraph G, Patharc P, ShortPathTable D){
     68     int i, j, k;
     69     // 二重循环,初始化P, D
     70     for(i = 0; i < G.numVertexes; ++i){
     71         for(j = 0; j < G.numVertexes; ++j){
     72             D[i][j] = G.arc[i][j];
     73             P[i][j] = j;
     74         }
     75     }
     76     // 三重循环, Floyd algorithm
     77     for(k = 0; k < G.numVertexes; ++k){
     78         for(i = 0; i < G.numVertexes; ++i){
     79             for(j = 0; j < G.numVertexes; ++j){
     80                 if(D[i][j] > D[i][k]+D[k][j]){
     81                     D[i][j] = D[i][k]+D[k][j];
     82                     P[i][j] = P[i][k];
     83                 }
     84             }
     85         }
     86     }
     87 }
     88 
     89 // 打印最短路径
     90 void PrintShortPath(MGraph G, Patharc P, ShortPathTable D){
     91     int i, j, k;
     92     cout<<"各顶点之间的最短路径如下: "<<endl;
     93     for(i = 0; i < G.numVertexes; ++i){
     94         for(j = i+1; j < G.numVertexes; ++j){
     95             cout<<"v"<<i<<"--"<<"v"<<j<<" "<<"weight: "<<D[i][j]<<"  Path: "<<i<<" -> ";
     96             k = P[i][j];
     97             while(k != j){
     98                 cout<<k<<" -> ";
     99                 k = P[k][j];
    100             }
    101             cout<<j<<endl;
    102         }
    103         cout<<endl;
    104     }
    105 }
    106 
    107 int main(int argc, char const *argv[]) {
    108     MGraph G;
    109     Patharc P;
    110     ShortPathTable D;
    111     CreateMGraph(&G);
    112     ShortPath_Floyd(G, P, D);
    113     PrintShortPath(G, P, D);
    114     return 0;
    115 }

    运行结果:

    各顶点之间的最短路径如下: 
    v0--v1 weight: 1  Path: 0 -> 1
    v0--v2 weight: 4  Path: 0 -> 1 -> 2
    v0--v3 weight: 7  Path: 0 -> 1 -> 2 -> 4 -> 3
    v0--v4 weight: 5  Path: 0 -> 1 -> 2 -> 4
    v0--v5 weight: 8  Path: 0 -> 1 -> 2 -> 4 -> 5
    v0--v6 weight: 10  Path: 0 -> 1 -> 2 -> 4 -> 3 -> 6
    v0--v7 weight: 12  Path: 0 -> 1 -> 2 -> 4 -> 3 -> 6 -> 7
    v0--v8 weight: 16  Path: 0 -> 1 -> 2 -> 4 -> 3 -> 6 -> 7 -> 8
    
    v1--v2 weight: 3  Path: 1 -> 2
    v1--v3 weight: 6  Path: 1 -> 2 -> 4 -> 3
    v1--v4 weight: 4  Path: 1 -> 2 -> 4
    v1--v5 weight: 7  Path: 1 -> 2 -> 4 -> 5
    v1--v6 weight: 9  Path: 1 -> 2 -> 4 -> 3 -> 6
    v1--v7 weight: 11  Path: 1 -> 2 -> 4 -> 3 -> 6 -> 7
    v1--v8 weight: 15  Path: 1 -> 2 -> 4 -> 3 -> 6 -> 7 -> 8
    
    v2--v3 weight: 3  Path: 2 -> 4 -> 3
    v2--v4 weight: 1  Path: 2 -> 4
    v2--v5 weight: 4  Path: 2 -> 4 -> 5
    v2--v6 weight: 6  Path: 2 -> 4 -> 3 -> 6
    v2--v7 weight: 8  Path: 2 -> 4 -> 3 -> 6 -> 7
    v2--v8 weight: 12  Path: 2 -> 4 -> 3 -> 6 -> 7 -> 8
    
    v3--v4 weight: 2  Path: 3 -> 4
    v3--v5 weight: 5  Path: 3 -> 4 -> 5
    v3--v6 weight: 3  Path: 3 -> 6
    v3--v7 weight: 5  Path: 3 -> 6 -> 7
    v3--v8 weight: 9  Path: 3 -> 6 -> 7 -> 8
    
    v4--v5 weight: 3  Path: 4 -> 5
    v4--v6 weight: 5  Path: 4 -> 3 -> 6
    v4--v7 weight: 7  Path: 4 -> 3 -> 6 -> 7
    v4--v8 weight: 11  Path: 4 -> 3 -> 6 -> 7 -> 8
    
    v5--v6 weight: 7  Path: 5 -> 7 -> 6
    v5--v7 weight: 5  Path: 5 -> 7
    v5--v8 weight: 9  Path: 5 -> 7 -> 8
    
    v6--v7 weight: 2  Path: 6 -> 7
    v6--v8 weight: 6  Path: 6 -> 7 -> 8
    
    v7--v8 weight: 4  Path: 7 -> 8
    
    
    [Finished in 1.2s]

    参考资料:

    大话数据结构

    Floyd–Warshall algorithm, Wikipedia

    Floyd Warshall Algorithm | DP-16 , geeksforgeeks  

  • 相关阅读:
    [背包问题][二进制优化] Jzoj P4224 食物
    [并查集][排序] Jzoj P4223 旅游
    [哈夫曼树][优先队列] Bzoj P4198 荷马史诗
    [hash][差分][虚树] Jzoj P6011 天天爱跑步
    [dp] Jzoj P6012 荷马史诗
    [dp][递归] Jzoj P4211 送你一棵圣诞树
    [数学] Jzoj P3912 超氧化钾
    堆学习笔记(未完待续)(洛谷p1090合并果子)
    [AC自动机]luogu P2444 病毒
    [概率期望][DP]luogu P3830 随机树
  • 原文地址:https://www.cnblogs.com/iwangzhengchao/p/10268027.html
Copyright © 2020-2023  润新知