「这是我参与2022首次更文挑战的第23天,活动详情查看:2022首次更文挑战」。
Floyd算法
每一对顶点的最短路径问题
【问题】给定带权有向图 G=(V, E) ,对任意顶点 vi 和vj(i ≠ j),求从顶点 vi 到顶点 vj 的最短路径
【算法】Floyd算法
Floyd算法——基本思想
w<vi, vj>:从顶点 vi 到顶点 vj 的权值
distk(vi, vj):从顶点 vi 到顶点 vj 经过的顶点编号不大于 k 的最短路径长度
Floyd算法描述
算法:Floyd算法
输入:带权有向图 G=(V,E)
输出:每一对顶点的最短路径
1. 初始化:假设从 vi 到 vj 的弧是最短路径,即dist-1(vi, vj)=w<vi, vj>;
2. 循环变量 k 从 0~n-1 进行 n 次迭代:
distk(vi, vj)=min{distk-1(vi, vj), distk-1(vi, vk)+distk-1(vk, vj)}
如何存储dist? 如何存储带权有向图?
邻接矩阵
dist-1(vi, vj) = w<vi, vj>
distk(vi, vj) = min{distk-1(vi, vj), distk-1(vi, vk)+distk-1(vk, vj)}
Floyd算法——运行实例
初始化
void Floyd(MGraph *G)
{
int i, j, k, dist[MaxSize][MaxSize];
for (i = 0; i < G->vertexNum; i++)
for (j = 0; j < G->vertexNum; j++)
dist[i][j] = G->edge[i][j];
}
经过v0
经过v1
经过v2
for (k = 0; k < G->vertexNum; k++)
for (i = 0; i < G->vertexNum; i++)
for (j = 0; j < G->vertexNum; j++)
if (dist[i][k] + dist[k][j] < dist[i][j])
dist[i][j] = dist[i][k] + dist[k][j];
Floyd算法-代码实现
void Floyd(MGraph *G)
{
int i, j, k, dist[MaxSize][MaxSize];
for (i = 0; i < G->vertexNum; i++)
for (j = 0; j < G->vertexNum; j++)
dist[i][j] = G->edge[i][j];
for (k = 0; k < G->vertexNum; k++)
for (i = 0; i < G->vertexNum; i++)
for (j = 0; j < G->vertexNum; j++)
if (dist[i][k] + dist[k][j] < dist[i][j])
dist[i][j] = dist[i][k] + dist[k][j];
Floyd算法性能分析
时间复杂度?
O(n3)