Floyd求最短路

概念

Floyd算法是一种解决图中所有点对之间最短路径的经典算法。使用动态规划的思想,通过中间节点逐步优化已知的最短路径。Floyd算法的核心思想是三层循环,对每一对节点(i, j)检查是否存在中间节点k,使得经过k节点的路径更短。如果存在这样的k,就更新(i, j)之间的最短路径

步骤

  1. 初始化: 构建一个二维数组dist,表示每一对节点之间的最短路径长度。若两节点之间存在直接连接,则dist[i][j]为直接路径长度,否则为无穷大。
  2. 动态规划更新: 使用三层循环遍历所有节点对(i, j),检查是否存在中间节点k,使得路径(i, k, j)比当前已知路径更短。如果是,则更新dist[i][j]
  3. 输出结果: 经过三层循环的迭代后,dist数组记录了所有节点对之间的最短路径长度。

模板

java 复制代码
// Assuming n is the number of nodes
// g[i][j] represents the weight of the edge between node i and node j
// Initialize g[i][j] as positive infinity for non-connected nodes

void floyd() {
    for (int k = 0; k < n; k++) {
        for (int i = 0; i < n; i++) {
            for (int j = 0; j < n; j++) {
                g[i][j] = Math.min(g[i][j], g[i][k] + g[k][j]);
            }
        }
    }
}
  • 如果节点的编号是从0开始,那么所有循环的范围应为for (int k = 0; k < n; k++)for (int i = 0; i < n; i++)for (int j = 0; j < n; j++)
  • g[i][j]应该初始化为正无穷大,表示节点i和节点j之间没有直接的连接。
  • g[i][i](对角线上的元素)应该初始化为0,表示节点到自身的距离为0。

题目应用

给定一个 n 个点 m 条边的有向图,图中可能存在重边和自环,边权可能为负数。

再给定 k 个询问,每个询问包含两个整数 x 和 y,表示查询从点 x 到点 y 的最短距离,如果路径不存在,则输出 impossible

数据保证图中不存在负权回路。

输入格式

第一行包含三个整数 n,m,k

接下来 m 行,每行包含三个整数 x,y,z表示存在一条从点 x 到点 y 的有向边,边长为 z

接下来 k 行,每行包含两个整数 x,y表示询问点 x 到点 y 的最短距离。

输出格式

共 k 行,每行输出一个整数,表示询问的结果,若询问两点间不存在路径,则输出 impossible

数据范围

  • 1≤n≤200
  • 1≤k≤n^2
  • 1≤m≤20000
  • 图中涉及边长绝对值均不超过 10000。

输入样例:

复制代码
3 3 2
1 2 1
2 3 2
1 3 1
2 1
1 3

输出样例:

复制代码
impossible
1

代码

java 复制代码
import java.util.Arrays;
import java.util.Scanner;

/**
 * 这道题的坑对我而言是顶点没从1开始,而是从0开始!
 */
public class Main {
    static int n, m , k, N = 210, max = (int)1e8;
    static int[][] g = new int[N][N];
    public static void main(String[] args) {
        Scanner in = new Scanner(System.in);
        n = in.nextInt();
        m = in.nextInt();
        k = in.nextInt();
        for (int i = 1;i <= n;i ++) {
            Arrays.fill(g[i], max);
        }
        for (int i = 1;i <= n;i ++) {
            g[i][i] = 0;
        }
        for (int i = 0;i < m;i ++) {
            int x = in.nextInt();
            int y = in.nextInt();
            int z = in.nextInt();
            g[x][y] = Math.min(g[x][y], z);
        }
        floyd();
        while (k > 0) {
            k--;
            int x = in.nextInt();
            int y = in.nextInt();
            if (g[x][y] > max / 2) {
                System.out.println("impossible");
            } else {
                System.out.println(g[x][y]);
            }
        }
    }
    public static void floyd() {
        for (int k = 1;k <= n;k ++) {
            for (int i = 1;i <= n;i ++) {
                for (int j = 1;j <= n;j ++) {
                    g[i][j] = Math.min(g[i][j], g[i][k] + g[k][j]);
                }
            }
        }
    }
}
相关推荐
小码哥_常8 小时前
MyBatis-Plus:让数据库操作飞起来的神器
后端
2301_811274319 小时前
基于SpringBoot的智能家居管理系统
spring boot·后端·智能家居
AI人工智能+电脑小能手9 小时前
【大白话说Java面试题】【Java基础篇】第15题:JDK1.7中HashMap扩容为什么会发生死循环?如何解决
java·开发语言·数据结构·后端·面试·哈希算法
舒一笑9 小时前
我把设备指纹生成逻辑拆开了:它到底凭什么区分不同设备?
后端·程序员·掘金技术征文
Nicander9 小时前
多数据源下@transcation事务踩坑
java·后端
郑州光合科技余经理9 小时前
同城O2O海外版二次开发实战:从支付网关到配送算法
开发语言·前端·后端·算法·架构·uni-app·php
sjsjsbbsbsn11 小时前
大模型核心知识总结
java·人工智能·后端
Moment11 小时前
2026 年,AI 全栈时代到了,前端简历别再只写前端技术了 🫠🫠🫠
前端·后端·面试
白晨并不是很能熬夜12 小时前
【PRC】第 2 篇:Netty 通信层 — NIO 模型 + 自定义协议 + 心跳
java·开发语言·后端·面试·rpc·php·nio
zshs00012 小时前
#从偶发无字幕到补偿探测链路:一次 B 站字幕导入问题的完整收敛过程
java·后端·重构