简介 :
- Floyd算法是解决任意两点间的最短路径的一种算法
- Floyd算法是一个经典的动态规划算法
- Floyd算法的时间复杂度为O(N3),空间复杂度为O(N2)
算法描述与原理:
首先我们的目标是寻找从点i到点j的最短路径。从一个节点 i 到 节点 j,无非就是两种情况
- 直接从 i 点 到 j 点
- 如 i 点出发经过若干个点到达 j 点
要找出最 i 节点 到 j 节点的最短距离,我们可以用dis(i,j)来表示 i 到 j的距离,对于 i 节点 到 j 节点 的每一个点 k ,我们可以得出
dis(i,k)+dis(k,j)<dis(i,j)
当这个式子成立时我们可以证明,i直接到j的距离不是最短距离,这时我们可以写出这样一个式子
dis(i,j)=dis(i,k)+dis(k,j)
这样的话 我们就只需要遍历所有节点 一次都进行上面的操作,这样dis(i,j) 就是 i 节点到 j 节点的最短距离
具体操作
- 对每两点的距离都赋予一个权值(在这里可以理解为距离)
- 对于每对点 x 和 y,判断是否有 一个顶点 x 到 z 再到 y的距离比直接x 到 y的距离要短
具体代码 :
import java.util.*;
import java.io.*;
public class Main{
private static final int MAX = 1<<29;
private static int[][] map;
private static Scanner scanner;
private static int num = 0,mum = 0;
static {
map = new int[100][100];
scanner = new Scanner(new BufferedInputStream(System.in));
}
public static void main(String[] args) {
while(scanner.hasNext()) {
num = scanner.nextInt();
mum = scanner.nextInt();
/*初始化数组*/
for (int i = 1; i<=num; i++) {
for (int j = 1; j<=num; j++) {
if (i!=j) {
map[i][j] = MAX;
}else {
map[i][j] = 0; //对于每个点自己到自己的权值(距离)为 0
}
}
}
/*手动添加每两个点之间的距离*/
for (int i = 1; i<=mum; i++) {
int x,y,z;
x = scanner.nextInt();
y = scanner.nextInt();
z = scanner.nextInt();
map[x][y] = z;
}
/* 核心算法,对于num个k 从 i 点 k点 再到 j点 与直接 i 到 j的距离相比较 取最小值*/
for (int k = 1;k <= num ; k++) {
for (int i = 1;i <= num ; i++) {
for (int j = 1; j <= num; j++) {
if (i!=j&&j!=k) {
map[i][j] = Math.min(map[i][j],map[i][k]+map[k][j]);
}
}
}
}
/* 打印 每两个点之间的最短路径*/
for (int i = 1; i <= num; i++ ) {
for (int j = 1; j <= num; j++ ) {
System.out.printf("dis %d %d = %d\n",i,j,map[i][j]);
}
}
}
}
}