只有5行的Floyd-Warshall算法

思想:每个点到其他点的最短路径都可以通过判断两个点之间是否可以通过其它点进行松 弛。

步骤:

   a.将图存储在二维数组map中(map数组中坐标为(a,b)代表点a到点b的最短路径)

   b.三层循环:

        第一层是循环每个点(意义在于判断是否可以通过该点刷新最短路径)(变量记为k)

        第二层是循环map数组的每一层(变量记为a)

        第三层是循环map数组每一层的每一列 (变量记为b)

  c.第三层循环中进行判断map[a][b]>map[a][k]+map[k][b],即判断是否可以通过b点刷新最短路径,这种操作叫做松弛。

代码示例:

import java.util.Arrays;
import java.util.Scanner;

/**
 输入:
6 9
0 1 1
0 2 12
1 2 9
1 3 3
2 4 5
3 2 4
3 4 13
3 5 15
4 5 4 
输出:
0点到0点的最短路径为:0
0点到1点的最短路径为:1
0点到2点的最短路径为:8
0点到3点的最短路径为:4
0点到4点的最短路径为:13
0点到5点的最短路径为:17
 *
 */

public class FloydShotestPath {

	public static void main(String[] args) {
		int[][] map;//这里定义一个的地图数组
		Scanner input = new Scanner(System.in);
		int point_number = input.nextInt(),side_number = input.nextInt();//输入点的个数和边的个数
		map = new int[point_number][point_number];
		for(int a=0;a<point_number;a++) {
			Arrays.fill(map[a], 999);//填充数组,所有值都为999代表点到点的距离都无穷大(不可直接达到)
			map[a][a] = 0;//代表点a到点a的距离为0
		}
		//输入每条边到map数组中
		for(int a=0;a<side_number;a++) {
			int start = input.nextInt();
			int end = input.nextInt();
			int value = input.nextInt();
			map[start][end] = value;
		}
		
		//算法核心,只有5行
		for(int a=0;a<point_number;a++) {//遍历每个点
			for(int b = 0;b<point_number;b++) {//遍历数组每一行
				for(int c=0;c<point_number;c++) {//遍历数组每行的每列
					if(map[b][c]>map[b][a]+map[a][c]) {//如果b→c的距离大于b→a+a→c,那么可以刷新数组中的值
						map[b][c] = map[b][a]+map[a][c];
					}
				}
			}
		}
		//这里只输出0点到各点的最短路径
		for(int a=0;a<point_number;a++) {
			System.out.println("0点到"+a+"点的最短路径为:"+map[0][a]);
		}
	}
	
}

算法特点:时间复杂度:N^3。可以处理带负权边的图,但不能处理负权回路

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值