zoukankan      html  css  js  c++  java
  • Floyd—Warshall算法

    我们用DP来求解任意两点间的最短路问题

    首先定义状态:d[k][i][k]表示使用顶点1~k,i,j的情况下,i到j的最短路径

    (d[0][i][j]表示只使用i和j,因此d[0][i][j] = cost[i][j]

    状态转移方程:d[k][i][j] = min ( d[k-1][i][k], d[k-1][k][j] )

    解释:我们分i到j的最短路正好经过顶点k一次和完全不经过k两种情况来讨论。

    这个DP也可以使用滚动数组来进行递推:d[i][j] = min ( d[i][j], d[i][k]+d[k][j] ),为什么可以这样呢?

    我参考了《算法竞赛入门经典》中对背包问题的滚动数组后大概就懂了,在计算d[k][i][j]之前,d[i][j]保存的是d[k-1][i][k],另外一个也是同样的道理

    模板如下:

    int d[MAX_V][MAX_V];//d[u][v]初始化时表示边e(u,v)的权值(不存在时设为INF,d[i][i]=0) 
    int V;//顶点数
     
    for (int k = 1; k <= V; k++)
        for (int i = 1; i <= V; i++)
            for (int j = 1; j <= V; j++)
                d[i][j] = min(d[i][j], d[i][k]+d[k][j]);

    附:

    滚动数组可处理的问题多表现为多步的数据递推,而且每一步递推只会用到上一次递推的数据,此时就记得要用滚动数组优化空间。

    由于每一步的递推只会用到上一步的数据,其常见的长度为2。

    可参考这篇博客:滚动数组

  • 相关阅读:
    vue组件通信类型限制
    vue父子组件通信
    vue组件data必须是函数
    vue组件模块抽离
    vue局部组件语法糖
    leetcode刷题-47全排列2
    leetcode刷题-46全排列
    leetcode刷题-43字符串相乘
    leetcode刷题-40组合总和2
    leetcode刷题-39组合总和
  • 原文地址:https://www.cnblogs.com/wizarderror/p/10914527.html
Copyright © 2011-2022 走看看