Dijkstra算法和Floyd算法求最短路径

1.Dijkstra算法
Dijkstra算法用于从一个起始节点到图中所有其他节点的最短路径。它使用贪心策略逐步扩展路径,并选择当前路径中最短的节点作为下一个节点。Dijkstra算法来计算起始节点到各个节点的最短距离。Dijkstra算法适用于有向图或无向图,但是对于权重为负的边,Dijkstra算法不适用。
求解步骤:①初始化距离数组和访问数组,将起始节点的距离值设置为0,其他节点的距离值设置为无穷大,访问数组初始化为false。②从起始节点开始,选择当前距离值最小的节点,将其标记为已访问。③遍历该节点的邻居节点,如果通过当前节点到达邻居节点的路径比之前的路径更短,则更新邻居节点的距离值。④重复上述步骤,选择下一个距离值最小的未访问节点,直到所有节点都被标记为已访问,或者找到了目标节点。输出最短路径结果,即起始节点到其他节点的最短距离。
代码示例

#include <stdio.h>
#include <stdbool.h>
#define INF 9999
#define V 6

void dijkstra(int graph[V][V], int start) {
    int dist[V]; // 存储起始节点到各个节点的最短距离
    bool visited[V]; // 记录节点是否已访问
    int i, j, min, u;
    
    // 初始化距离数组和访问数组
    for (i = 0; i < V; i++) {
        dist[i] = INF;
        visited[i] = false;
    }
    
    // 设置起始节点距离为0
    dist[start] = 0;
    
    // 寻找最短路径
    for (i = 0; i < V - 1; i++) {
        min = INF;
        for (j = 0; j < V; j++) {
            if (!visited[j] && dist[j] < min) {
                min = dist[j];
                u = j;
            }
        }
        
        visited[u] = true;
        
        for (j = 0; j < V; j++) {
            if (!visited[j] && graph[u][j] != INF && dist[u] + graph[u][j] < dist[j]) {
                dist[j] = dist[u] + graph[u][j];
            }
        }
    }
    
    // 打印最短路径结果
    printf("节点  最短距离n");
    for (i = 0; i < V; i++) {
        printf("%d %dn", i, dist[i]);
    }
}

int main() {
    int graph[V][V] = {
        {0, 1, 4, INF, INF, INF},
        {1, 0, 2, 7, 5, INF},
        {4, 2, 0, INF, 1, INF},
        {INF, 7, INF, 0, 3, 2},
        {INF, 5, 1, 3, 0, 6},
        {INF, INF, INF, 2, 6, 0}
    };
    
    int start = 0; // 起始节点
    dijkstra(graph, start);
    
    return 0;
}

2.Floyd算法:
Floyd算法用于计算图中任意两个节点之间的最短路径。它采用动态规划的思想,通过中间节点的遍历来更新最短路径。适用于有向图或无向图,并且可以处理权重为负的边,但是对于包含负权重环的图,Floyd-Warshall算法不适用。
求解步骤:①初始化距离矩阵,其中的元素表示两个节点之间的直接距离。如果两个节点之间没有直接连接,则距离为无穷大。②使用动态规划的思想,通过中间节点的遍历来更新节点之间的最短路径。③对于每一对节点,通过考虑是否经过一个中间节点,更新它们之间的距离。如果通过中间节点得到的路径比之前的路径更短,则更新距离矩阵中的值。④重复上述步骤,遍历所有的节点作为中间节点。
输出最短路径结果,即任意两个节点之间的最短距离。
代码示例:

#include <stdio.h>
#define INF 9999
#define V 4

void floydWarshall(int graph[V][V]) {
    int dist[V][V]; // 存储最短路径距离
    int i, j, k;
    
    // 初始化距离数组
    for (i = 0; i < V; i++) {
        for (j = 0; j < V; j++) {
            dist[i][j] = graph[i][j];
        }
    }
    
    // 寻找最短路径
    for (k = 0; k < V; k++) {
        for (i = 0; i < V; i++) {
            for (j = 0; j < V; j++) {
                if (dist[i抱歉,上面的代码截断了。以下是完整的Floyd-Warshall算法的C语言代码示例:

```c
#include <stdio.h>
#define INF 9999
#define V 4

void floydWarshall(int graph[V][V]) {
    int dist[V][V]; // 存储最短路径距离
    int i, j, k;

    // 初始化距离数组
    for (i = 0; i < V; i++) {
        for (j = 0; j < V; j++) {
            dist[i][j] = graph[i][j];
        }
    }

    // 寻找最短路径
    for (k = 0; k < V; k++) {
        for (i = 0; i < V; i++) {
            for (j = 0; j < V; j++) {
                if (dist[i][k] + dist[k][j] < dist[i][j]) {
                    dist[i][j] = dist[i][k] + dist[k][j];
                }
            }
        }
    }

    // 打印最短路径结果
    printf("节点对t最短距离n");
    for (i = 0; i < V; i++) {
        for (j = 0; j < V; j++) {
            if (dist[i][j] == INF) {
                printf("%d 到 %dtINFn", i, j);
            } else {
                printf("%d 到 %dt%dn", i, j, dist[i][j]);
            }
        }
    }
}

int main() {
    int graph[V][V] = {
        {0, 3, INF, 7},
        {8, 0, 2, INF},
        {5, INF, 0, 1},
        {2, INF, INF, 0}
    };

    floydWarshall(graph);

    return 0;
}