数据结构:点之间的最短距离--Floyd算法

                           Floyd算法

Floyd算法

    Dijkstra算法是用于解决单源最短路径问题的,Floyd算法则是解决点对之间最短路径问题的。Floyd算法的设计策略是动态规划,而Dijkstra採取的是贪心策略。当然,贪心算法就是动态规划的特例。

算法思想

    点对之间的最短路径仅仅会有两种情况:

  1. 两点之间有边相连。weight(Vi,Vj)即是最小的。

  2. 通过还有一点:中介点,两点相连,使weight(Vi,Vv)+weight(Vv,Vj)最小。

Min_Distance(Vi,Vj)=min{weight(Vi,Vj),weight(Vi,Vv)+weight(Vv,Vj)}。正是基于这样的背后的逻辑。再加上动态规划的思想,构成了Floyd算法。

故当Vv取全然部顶点后,Distance(Vi,Vj)就可以达到最小。Floyd算法的起点就是图的邻接矩阵。


题外话:代码本身不重要。算法思想才是精髓。

思想极难得到,而有了思想,稍加经验就可以写出代码。向思想的开创者致敬。


思想非常难。代码却比較简单。直接上代码

代码

类定义
#include<iostream>  
#include<iomanip>
#include<stack>
using namespace std;
#define MAXWEIGHT 100
#undef INFINITY
#define INFINITY 1000
class Graph
{
private://顶点数  int numV;//边数  int numE;//邻接矩阵  int **matrix;
public:Graph(int numV);//建图  void createGraph(int numE);//析构方法  ~Graph();//Floyd算法void Floyd();//打印邻接矩阵  void printAdjacentMatrix();//检查输入  bool check(int, int, int);
};
类实现
//构造函数,指定顶点数目
Graph::Graph(int numV)
{//对输入的顶点数进行检測while (numV <= 0){cout << "顶点数有误!

又一次输入 "; cin >> numV; } this->numV = numV; //构建邻接矩阵。并初始化 matrix = new int*[numV]; int i, j; for (i = 0; i < numV; i++) matrix[i] = new int[numV]; for (i = 0; i < numV; i++) for (j = 0; j < numV; j++) { if (i == j) matrix[i][i] = 0; else matrix[i][j] = INFINITY; } } void Graph::createGraph(int numE) { /* 对输入的边数做检測 一个numV个顶点的有向图,最多有numV*(numV - 1)条边 */ while (numE < 0 || numE > numV*(numV - 1)) { cout << "边数有问题!又一次输入 "; cin >> numE; } this->numE = numE; int tail, head, weight, i; i = 0; cout << "输入每条边的起点(弧尾)、终点(弧头)和权值" << endl; while (i < numE) { cin >> tail >> head >> weight; while (!check(tail, head, weight)) { cout << "输入的边不对!请又一次输入 " << endl; cin >> tail >> head >> weight; } matrix[tail][head] = weight; i++; } } Graph::~Graph() { int i; for (i = 0; i < numV; i++) delete[] matrix[i]; delete[]matrix; } /* 弗洛伊德算法 求各顶点对之间的最短距离 及其路径 */ void Graph::Floyd() { //为了不改动邻接矩阵,多用一个二维数组 int **Distance = new int*[numV]; int i, j; for (i = 0; i < numV; i++) Distance[i] = new int[numV]; //初始化 for (i = 0; i < numV; i++) for (j = 0; j < numV; j++) Distance[i][j] = matrix[i][j]; //prev数组 int **prev = new int*[numV]; for (i = 0; i < numV; i++) prev[i] = new int[numV]; //初始化prev for (i = 0; i < numV; i++) for (j = 0; j < numV; j++) { if (matrix[i][j] == INFINITY) prev[i][j] = -1; else prev[i][j] = i; } int d, v; for (v = 0; v < numV; v++) for (i = 0; i < numV; i++) for (j = 0; j < numV; j++) { d = Distance[i][v] + Distance[v][j]; if (d < Distance[i][j]) { Distance[i][j] = d; prev[i][j] = v; } } //打印Distance和prev数组 cout << "Distance..." << endl; for (i = 0; i < numV; i++) { for (j = 0; j < numV; j++) cout << setw(3) << Distance[i][j]; cout << endl; } cout << endl << "prev..." << endl; for (i = 0; i < numV; i++) { for (j = 0; j < numV; j++) cout << setw(3) << prev[i][j]; cout << endl; } cout << endl; //打印顶点对最短路径 stack<int> s; for (i = 0; i < numV; i++) { for (j = 0; j < numV; j++) { if (Distance[i][j] == 0); else if (Distance[i][j] == INFINITY) cout << "顶点 " << i << " 到顶点 " << j << " 无路径!

" << endl; else { s.push(j); v = j; do{ v = prev[i][v]; s.push(v); } while (v != i); //打印路径 cout << "顶点 " << i << " 到顶点 " << j << " 的最短路径长度是 " << Distance[i][j] << " ,其路径序列是..."; while (!s.empty()) { cout << setw(3) << s.top(); s.pop(); } cout << endl; } } cout << endl; } //释放空间 for (i = 0; i < numV; i++) { delete[] Distance[i]; delete[] prev[i]; } delete[]Distance; delete[]prev; } //打印邻接矩阵 void Graph::printAdjacentMatrix() { int i, j; cout.setf(ios::left); cout << setw(7) << " "; for (i = 0; i < numV; i++) cout << setw(7) << i; cout << endl; for (i = 0; i < numV; i++) { cout << setw(7) << i; for (j = 0; j < numV; j++) cout << setw(7) << matrix[i][j]; cout << endl; } } bool Graph::check(int tail, int head, int weight) { if (tail < 0 || tail >= numV || head < 0 || head >= numV || weight <= 0 || weight >= MAXWEIGHT) return false; return true; }

主函数
int main()
{cout << "******Floyd***by David***" << endl;int numV, numE;cout << "建图..." << endl;cout << "输入顶点数 ";cin >> numV;Graph graph(numV);cout << "输入边数 ";cin >> numE;graph.createGraph(numE);cout << endl << "Floyd..." << endl;graph.Floyd();system("pause");return 0;
}
执行



小结

Floyd算法代码看似非常长,事实上并不难。代码中非常多都是用于准备工作和输出。关键代码就是三层for循环。


完整代码下载:Floyd算法

转载请注明出处,本文地址:http://blog.csdn.net/zhangxiangdavaid/article/details/38366923

若有所帮助,顶一个哦。

专栏文件夹:
  • 数据结构与算法文件夹
  • c指针

版权声明:本文博主原创文章。转载,转载请注明出处。

转载于:https://www.cnblogs.com/gcczhongduan/p/4850988.html

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/431296.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

shell 获取家目录_一篇教会你写90%的shell脚本

shell是外壳的意思&#xff0c;就是操作系统的外壳。我们可以通过shell命令来操作和控制操作系统&#xff0c;比如Linux中的Shell命令就包括ls、cd、pwd等等。总结来说&#xff0c;Shell是一个命令解释器&#xff0c;它通过接受用户输入的Shell命令来启动、暂停、停止程序的运行…

数据结构c语言版第四章题库,数据结构(C语言版)(第4版)习题

数据结构(C语言版)(第4版)习题 习题 11.1 选择题。(1)计算机识别、存储和加工处理的对象统称为 。A&#xff0e;数据 B.数据元素 C.数据结构 D.数据类型(2)数据结构通常是研究数据的 及它们之间的联系。A&#xff0e;存储和逻辑结构 B.存储和抽象 C.理想和抽象 D.理想和逻辑(3)…

C++刷称号——2707: 素数与要素

Description 从键盘输入的随机整数n&#xff0c;如果n不是质数&#xff0c;然后计算n所有的因素&#xff08;不含1&#xff09;。例如&#xff0c;对于16&#xff0c;出口2,4,8&#xff1b;否则输出“It is a prime number.” 推断素数和需求因素已完成功能。 Input 随机整数n …

python opencv输出mp4_Python玩转视频处理(四):视频按场景进行分割

在上一篇文章&#xff08;python在手&#xff0c;女神视频轻松有&#xff09;分享了用AI人脸识别技术标记人物出现时间点来截取视频片段的教程&#xff0c;它的局限性在于只能通过识别特定的对象&#xff08;比如人脸&#xff09;来操作。在本文中将分享一个按场景进行分割视频…

stm32 isp下载官方软件android_OpenCanvas免费版下载_OpenCanvas绘图软件官方版下载7.0.25...

OpenCanvas 是一款小巧的CG手绘软件&#xff0c;让用户在使用数位板在电脑上绘图时&#xff0c;就像是在纸上手绘一样&#xff0c;可以画出极为细致的图像。OpenCanvas功能简捷、体积小巧、运行速度快&#xff0c;大家可以很快上手&#xff0c;非常适合入门级手绘爱好者使用。对…

【转】图文详解YUV420数据格式

YUV格式有两大类&#xff1a;planar和packed。 对于planar的YUV格式&#xff0c;先连续存储所有像素点的Y&#xff0c;紧接着存储所有像素点的U&#xff0c;随后是所有像素点的V。对于packed的YUV格式&#xff0c;每个像素点的Y,U,V是连续交*存储的。 YUV&#xff0c;分为三个分…

python安装pip_在MAC下安装pip,并关联到相应的python版本

在MAC下安装pip&#xff0c;并关联到相应的python版本 博客说明 文章所涉及的资料来自互联网整理和个人总结&#xff0c;意在于个人学习和经验汇总&#xff0c;如有什么地方侵权&#xff0c;请联系本人删除&#xff0c;谢谢&#xff01; 说明 不多说了&#xff0c;说就是电脑重…

cat命令详解_好程序员Python培训之详解eval好与坏

好程序员Python培训之详解eval好与坏&#xff0c;文中通过示例代码介绍的非常详细&#xff0c;对大家的学习或者工作具有一定的参考学习价值&#xff0c;下面我们一起来看一下吧。eval是Python的一个内置函数&#xff0c;这个函数的作用是&#xff0c;返回传入字符串的表达式的…

对代理商的评价怎么写_简历中的自我评价怎么写才能更吸引人?

有统计报告显示&#xff1a;HR每天看到的职位简历至少1000&#xff0c;每封简历的停留时间不过10秒。在这么短的时间内&#xff0c;让hr印象深刻&#xff0c;自我评价的价值就出现啦&#xff01;不少人认为自我评价要幽默风趣&#xff0c;例如&#xff1a;“您都看到这儿了&…

sdk是什么_人脸识别在美颜SDK中存在什么意义?

在得益于短视频、直播平台的飞速发展下&#xff0c;美颜SDK也得到了很大的发展&#xff0c;变得越来越受欢迎。美颜SDK现在已经融入到我们的生活&#xff0c;是社交中必不可少的工具。现在人们对于美颜的要求越来越高&#xff0c;这就意味着美颜SDK的质量也要越来越好。而人脸识…

socket工具android,Android通过socket长连接实现推送

工具&#xff1a;Android studio软件方法及协议&#xff1a;socket、protobuf实现原理&#xff1a;通过本地建立一个socket&#xff0c;绑定服务器IP和port&#xff0c;然后connect&#xff0c;再开启另外线程定时心跳(注意这里的心跳不是自定义发送数据&#xff0c;而是采用so…

一行代码为UITextField添加收键盘功能

iOS开发中收键盘是十分常用的功能&#xff0c;只需一行代码即可为ViewController添加工具条收键盘功能 更重要的是使用catogory&#xff0c;无代码污染。 代码 // UITextFieldkeyboard.h // TextFieldKeyBord // // Created by luo.h on 15/10/8. // Copyright © 2015…

excel一列求和_【excel每日提升】Excel周日不排班!

【新朋友】点击标题下面蓝色字“王俊东“关注。 【老朋友】点击右上角&#xff0c;转发或分享本页面内容。excel系列课程excel特效系列课程&#xff01;第1节&#xff1a;Excel有公式的单元格标记颜色&#xff0c;很简单&#xff01;第2节&#xff1a;Excel删除空行&#xff0…

android 减速动画,Android View Animation

概述可译为视图动画&#xff0c;分为缩放动画平移动画渐变动画旋转动画Android系统中定义了一个抽象类Animation来定义这种视图动画&#xff0c;它的具体子类如下表&#xff1a;动画名称对应的子类xml中标签描述缩放动画ScaleAnimation< scale />S平移动画TranslateAnima…

excel排名_Excel案例:比赛中,如何实时显示排名

其实今天的重点&#xff0c;是要借这个常规比赛记分与公布的案例&#xff0c;介绍一下数组函数&#xff01;今天的案例&#xff0c;最关键的地方只用了一次数组函数就搞定了&#xff01;------分-----割-----线-----下面进入案例&#xff1a;常见的比赛&#xff0c;有很评委一起…

node 存储过程_用Node.js操作跨平台数据库Firebird

FireBirdFirebird是一个跨平台的关系数据库系统&#xff0c;目前能够运行在Windows、linux和各种Unix操作系统上&#xff0c;提供了大部分SQL-99标准的功能。它既能作为多用户环境下的数据库服务器运行&#xff0c;也提供嵌入式数据库的实现。Firebird脱胎于Borland公司的开源版…

鸿蒙是内核名字,华为徐直军:鸿蒙只是内核的名字,是媒体给误解成操作系统...

集微网消息(文/Jimmy)&#xff0c;华为轮值董事徐直军表示鸿蒙操作系统名字是媒体取得&#xff0c;华为并没打算取这个名字。他解释称&#xff0c;本来鸿蒙这个是用于华为内部一个内核的名字&#xff0c;只是挂在市场监管总局那里注册了。然后不知道哪个媒体好朋友看到了这个&a…

手机进程设置多少个最好_安卓手机难逃卡顿宿命?打开4个系统设置,秒变新机般流畅...

近两年安卓手机的进步无疑的巨大的&#xff0c;不论是界面美观性、系统流畅度&#xff0c;还是功能的丰富性都有很大的进步&#xff0c;但是针对安卓的旧设备&#xff0c;用了两三年依旧开始变得卡顿&#xff0c;难道安卓手机真的难逃卡顿的宿命吗&#xff1f;虽然不能解决&…

html5新增的js,HTML5新增属性data-*和js/jquery之间的交互及注意事项

html的data-*属性是HTML5的新属性&#xff0c;用的时候在IE8html的data-*属性是HTML5的新属性&#xff0c;用来自定义属性&#xff0c;以在JS 中控制&#xff0c;用不会出问题&#xff0c;就是用js去获得的时候会有问题&#xff0c; 不过用Jquery的$(element).attr("data-…

韦东山 IMX6ULL和正点原子_GPIO和Pinctrl子系统的使用在100ASK_IMX6ULL上机实验

来源&#xff1a;百问网作者&#xff1a;韦东山本文字数&#xff1a;924&#xff0c;阅读时长&#xff1a;3分钟阅读本节前先阅读&#xff1a;Pinctrl子系统重要概念GPIO子系统重要概念基于GPIO子系统的LED驱动程序1.1 确定引脚并生成设备树节点NXP公司对于IMX6ULL芯片&#xf…