简介:Floyd算法又称为插点法,是一种利用动态规划的思想寻找给定的加权图中多源点之间最短路径的算法,与Dijkstra算法类似。该算法名称以创始人之一、1978年图灵奖获得者、斯坦福大学计算机科学系教授罗伯特·弗洛伊德命名。


eg:暑假,小哼准备去一些城市旅游。有些城市之间有公路,有些城市之间则没有,如下图。为了节省经费及方便计划旅程,小哼希望在出发前知道任意两个城市之间的最短路程。

上图中有4个城市8条公路,公路上的数字表示这条公路的长短。请注意这些公路是单向的。我们现在需要求任意两个城市之间的最短路程,也就是求任意两个点之间的最短路径。这个问题这也被称为“多源最短路径”问题。现在需要一个数据结构来存储图的信息,我们仍然可以用一个4*4的矩阵(二维数组e)来存储。比如1号城市到2号城市的路程为2,则设e[1][2]的值为2。2号城市无法到达4号城市,则设置e[2][4]的值为∞。另外此处约定一个城市自己是到自己的也是0,例如e[1][1]为0。


我们回到最开始的问题,最短路径问题,如何求任意两点之间的最短路径呢?

我们通过之前的学习,我们知道通过深搜或者广搜都可以求出两点的最短路径,所以进行n^2 遍深搜或广搜,即对每个点都进行一次深搜或者广搜,我们就可以求得最短路径。但是我们最常用求最短路径的算法的就是bellman-ford,dijkstra,spfa,floyd算法。

如果求任意两点之间的最短路径,两点之间可以直接到达但却不是最短的路径,要让任意两点(例如从顶点a点到顶点b)之间的路程变短,只能引入第三个点(顶点k),并通过这个顶点k中转即a->k->b,才可能缩短原来从顶点a点到顶点b的路程。那么这个中转的顶点k是1~n中的哪个点呢?甚至有时候不只通过一个点,而是经过两个点或者更多点中转会更短。比如上图中从4号城市到3号城市(4->3)的路程e[4][3]原本是12。如果只通过1号城市中转(4->1->3),路程将缩短为11(e[4][1]+e[1][3]=5+6=11)。其实1号城市到3号城市也可以通过2号城市中转,使得1号到3号城市的路程缩短为5(e[1][2]+e[2][3]=2+3=5)。所以如果同时经过1号和2号两个城市中转的话,从4号城市到3号城市的路程会进一步缩短为10。通过这个的例子,我们发现每个顶点都有可能使得另外两个顶点之间的路程变短。好,下面我们将这个问题一般化。

当任意两点之间不允许经过第三个点时,这些城市之间最短路程就是初始路程,如下:

假如现在只允许经过1号顶点,求任意两点的最短路径我们应该怎么求呢??

此时我们只需判断e[i][1] + e[1][j] 是否比e[i][j] 要小即可。我们来说明一下e[i][j] 和 e[i][1] + e[1][j] 表示的是什么意思,e[i][j] 就是便是从I号定点到 j 号顶点之间的路程,e[i][1] + e[1][j] 表示的是从 i 号顶点到 1 号顶点,再从1号顶点到 j 号顶点的路径之和。

在这其中,I是从1n循环,j也是从1n循环,具体这一步的实现代码如下。


在只允许过 1号顶点的情况下,任意两点之间的路程更新为:

通过上图我们发现,在只通过1号顶点中转的情况下,3号和2号顶点(e[3][2])、4号顶点到2号顶点(e[4][2])以及4号顶点到3号顶点(e[4][3])的路程都变短了。

接下来继续求在只允许经过1和2号两个顶点的情况下任意两点之间的最短路程。如何做呢?我们需要在只允许经过1号顶点时任意两点的最短路程的结果下,再判断如果经过2号顶点是否可以使得i号顶点到j号顶点之间的路程变得更短。即判断 e[i][2] + e[2][j] 是否比 e[i][j] 要小,具体实现代码如下:


在只允许更新1号和2号顶点的情况下,任意两点之间的路径更新为:


通过上图我们可以看出来,在相比只允许1号顶点进行中转的情况,这里允许通过1号和2号顶点进行中转,使得e[1][3] 和e[4][3]的路程变得更短了。

同理,我们在只允许通过1,2,3号顶点的情况下,求任意两点之间的最短路程。任意两点的最短路程更新为:


最后是允许所有顶点作为中转,任意两点的最终路程为:


整个算法过程虽然说起来很麻烦,但是核心代码就那么几行,不信你看:

这个代码的基本思路就是我们从最开始的只允许经过1号顶点进行中转,接下来只允许1,2进行中转。。。。。允许经过1~n 号所有的顶点进行中转,求任意两点的最短路径。

这个算法的完整代码:


我们来分析一下算法:

Floyd优缺点分析:

优点:比较容易容易理解,可以算出任意两个节点之间的最短距离,代码编写简单。
缺点:时间复杂度比较高(n3),不适合计算大量数据,当数据稍微大点儿的时候就可以选择其他的算法来解决问题了,不然也会是超时。

Floyd算法与Dijkstra算法的不同

1.Floyd算法是求任意两点之间的距离,是多源最短路,而Dijkstra(迪杰斯特拉)算法是求一个顶点到其他所有顶点的最短路径,是单源最短路。
2.Floyd算法属于动态规划,我们在写核心代码时候就是相当于推dp状态方程,Dijkstra(迪杰斯特拉)算法属于贪心算法。
3.Dijkstra(迪杰斯特拉)算法时间复杂度一般是o(n2),Floyd算法时间复杂度是o(n3),Dijkstra(迪杰斯特拉)算法比Floyd算法块。
4.Floyd算法可以算带负权的,而Dijkstra(迪杰斯特拉)算法是不可以算带负权的。并且Floyd算法不能算负权回路。

https://haokan.baidu.com/v?vid=15284978659146216535&pd=bjh&fr=bjhauthor&type=video


1.构建邻接矩阵 (没有直接相连的 距离为无穷大)
2.path 01 代表 从0到1
3.考虑把每个结点作为中转结点 ,其他两个节点之间通过它中转
之后的总的路径 是否比二者直连的距离要短,如果是用新的短距离
覆盖原来的直连值,路径也改成二者的组合
4.考虑完所有的点作为中转点
5.得到任意两点间的最短距离

Warshall算法多源点之间最短路径的算法最短距离相关推荐

  1. python棋盘最短路径_Python数据结构与算法之图的最短路径(Dijkstra算法)完整实例...

    本文实例讲述了Python数据结构与算法之图的最短路径(Dijkstra算法).分享给大家供大家参考,具体如下: # coding:utf-8 # Dijkstra算法--通过边实现松弛 # 指定一个 ...

  2. JAVA编程求单源最短路径_【算法】单源最短路径——dijkstra算法

    一,概念 单源最短路径 给定一个带权有向图G=(V,E),其中每条边的权是一个实数.另外,还给定V中的一个顶点,称为源.要计算从源到其他所有各顶点的最短路径长度.这里的长度就是指路上各边权之和.这个问 ...

  3. 求两点之间最短路径-Dijkstra算法

     Dijkstra算法 1.定义概览 Dijkstra(迪杰斯特拉)算法是典型的单源最短路径算法,用于计算一个节点到其他所有节点的最短路径.主要特点是以起始点为中心向外层层扩展,直到扩展到终点为止.D ...

  4. PostgreSQL+PostGIS实现两坐标点之间最短路径查询算法函数(地图工具篇.12)

    听老人家说:多看美女会长寿 地图之家总目录(订阅之前建议先查看该博客) 前置博客地址: 11.(地图工具篇)PostgreSQL+PostGIS实现最短路径分析 1.测试验证 select routi ...

  5. 最短路径BFS算法matlab,迷宫的最短路径 bfs算法

    题目描述: 给定一个大小为N*M的迷宫,由通道(.)和墙壁(#)组成,其中通道S表示起点,通道G表示终点,每一次移动可以到达上下左右中不是墙壁的位置.试求出起点到终点的最小步数. 样例输入输出: 思路 ...

  6. 最短路径(Floyd算法)(c/c++)

    如果要得到图中各个顶点之间的最短路径,方法1:可以对每一个顶点采用Dijkstra算法:方法2:可以采用Floyd算法,它是一种用来求双源点之间最短路径的算法,采用邻接矩阵来存储图 辅助结构 int ...

  7. 【最短路径Floyd算法详解推导过程】看完这篇,你还能不懂Floyd算法?还不会?...

    简介 Floyd-Warshall算法(Floyd-Warshall algorithm),是一种利用动态规划的思想寻找给定的加权图中多源点之间最短路径的算法,与Dijkstra算法类似.该算法名称以 ...

  8. 求解两点间最短路径的算法

    最短路径算法 1.Dijkstra算法 2.Bellman-Ford算法 3.SPFA算法 4.Floyd算法 几种最短路径算法的对比 Dijkstra算法.Bellman-Ford算法和SPFA算法 ...

  9. 最短路径——Floyd算法

    1. 背景: Floyd算法又称为插点法,是一种利用动态规划的思想寻找给定的加权图中多源点之间最短路径的算法,与Dijkstra算法类似.该算法名称以创始人之一.1978年图灵奖获得者.斯坦福大学计算 ...

最新文章

  1. 网站权重增加需要做的
  2. 数据的标准化和标准化方法
  3. sprint周期总结
  4. 解决方案需求提升 安防工程细节化事项要了解
  5. [res].xml格式
  6. from import 导入时找不到module的解决办法(Python模块包中_init_.py文件的作用)
  7. 用猎物皮毛换酒喝java_荒野大镖客2三星毛皮狩猎技巧分享 各种类猎物三星皮毛获取方法...
  8. ubuntu切换root用户
  9. 【OpenCV 例程200篇】52. 图像的相关与卷积运算
  10. php更改txt文件,如何使用php对txt文件进行修改
  11. [导入]Manning.Ajax.in.Action.Oct.2005.pdf(9.26 MB)
  12. 如何解除国外听QQ音乐网易音乐地区版权限制解除
  13. RK3288 USB触摸屏无法使用,需要添加PID和VID
  14. 索尼Z2强刷固件教程
  15. 电子合同助力“在线教育”高效发展
  16. vue + element插件Popover弹出框
  17. c语言中1 2 3怎么运算符号,C语言运算符和表达式(一)
  18. 计算机为什么采用二进制
  19. 黎曼ζ(2)的导数:ζ'(2)=-1
  20. apache poi excel word 加密,不用借助其他jxcell.jar包

热门文章

  1. 2022-2028年中国激光玻璃行业市场供需规模及发展趋势研究报告
  2. Solr 使用Facet分组过程中与分词的矛盾解决办法
  3. Go 学习笔记(63)— Go 中的 for ... range 对切片和数组的差异
  4. 文件句柄和文件描述符的区别和理解指针
  5. Python关于%matplotlib inline
  6. Python中常见字符串去除空格的方法总结
  7. 请注意更新TensorFlow 2.0的旧代码
  8. Transformer的PyTorch实现
  9. LeetCode简单题之统计匹配检索规则的物品数量
  10. Laravel中Redis的配置和使用