Dijkstra算法图文详解

2023-05-16

Dijkstra算法算是贪心思想实现的,首先把起点到所有点的距离存下来找个最短的,然后松弛一次再找出最短的,所谓的松弛操作就是,遍历一遍看通过刚刚找到的距离最短的点作为中转站会不会更近,如果更近了就更新距离,这样把所有的点找遍之后就存下了起点到其他所有点的最短距离。

迪杰斯特拉(Dijkstra)算法是典型最短路径算法,用于计算一个节点到其他节点的最短路径。它的主要特点是以起始点为中心向外层层扩展(广度优先搜索思想),直到扩展到终点为止。

这样一个有权图,Dijkstra算法可以计算任意节点到其他节点的最短路径
在这里插入图片描述

算法思路

1.指定一个节点,例如我们要计算 ‘A’ 到其他节点的最短路径

2.引入两个集合(S、U),S集合包含已求出的最短路径的点(以及相应的最短长度),U集合包含未求出最短路径的点(以及A到该点的路径,注意 如上图所示,A->C由于没有直接相连 初始时为∞)

3.初始化两个集合,S集合初始时 只有当前要计算的节点,A->A = 0,U集合初始时为 A->B = 4, A->C = ∞, A->D = 2, A->E = ∞,敲黑板!!!接下来要进行核心两步骤了

4.从U集合中找出路径最短的点,加入S集合,例如 A->D = 2

5.更新U集合路径,if ( ‘D 到 B,C,E 的距离’ + ‘AD 距离’ < ‘A 到 B,C,E 的距离’ ) 则更新U

6.循环执行 4、5 两步骤,直至遍历结束,得到A 到其他节点的最短路径

算法图解

1.选定A节点并初始化,如上述步骤3所示
在这里插入图片描述
2.执行上述 4、5两步骤,找出U集合中路径最短的节点D 加入S集合,并根据条件 if ( ‘D 到 B,C,E 的距离’ + ‘AD 距离’ < ‘A 到 B,C,E 的距离’ ) 来更新U集合
在这里插入图片描述
3.这时候 A->B, A->C 都为3,没关系。其实这时候他俩都是最短距离,如果从算法逻辑来讲的话,会先取到B点。而这个时候 if 条件变成了 if ( ‘B 到 C,E 的距离’ + ‘AB 距离’ < ‘A 到 C,E 的距离’ ) ,如图所示这时候A->B距离 其实为 A->D->B

例二.这个图表示的也非常清楚。
(以第4个顶点D为起点)
在这里插入图片描述
初始状态:S是已计算出最短路径的顶点集合,U是未计算除最短路径的顶点的集合!
第1步:将顶点D加入到S中。
此时,S={D(0)}, U={A(∞),B(∞),C(3),E(4),F(∞),G(∞)}。 注:C(3)表示C到起点D的距离是3。

第2步:将顶点C加入到S中。
上一步操作之后,U中顶点C到起点D的距离最短;因此,将C加入到S中,同时更新U中顶点的距离。以顶点F为例,之前F到D的距离为∞;但是将C加入到S之后,F到D的距离为9=(F,C)+(C,D)。
此时,S={D(0),C(3)}, U={A(∞),B(13),E(4),F(9),G(∞)}。

第3步:将顶点E加入到S中。
上一步操作之后,U中顶点E到起点D的距离最短;因此,将E加入到S中,同时更新U中顶点的距离。还是以顶点F为例,之前F到D的距离为9;但是将E加入到S之后,F到D的距离为6=(F,E)+(E,D)。
此时,S={D(0),C(3),E(4)}, U={A(∞),B(13),F(6),G(12)}。

第4步:将顶点F加入到S中。
此时,S={D(0),C(3),E(4),F(6)}, U={A(22),B(13),G(12)}。

第5步:将顶点G加入到S中。
此时,S={D(0),C(3),E(4),F(6),G(12)}, U={A(22),B(13)}。

第6步:将顶点B加入到S中。
此时,S={D(0),C(3),E(4),F(6),G(12),B(13)}, U={A(22)}。

第7步:将顶点A加入到S中。
此时,S={D(0),C(3),E(4),F(6),G(12),B(13),A(22)}。

此时,起点D到各个顶点的最短距离就计算出来了:A(22) B(13) C(3) D(0) E(4) F(6) G(12)。

Dijkstra算法与路径规划

Dijkstra算法是很有代表性的最短路径规划算法。一般的表述通常有两种方式,一种用永久和临时标号方式,一种是用OPEN, CLOSE表方式,路径规划采用OPEN,CLOSE表的方式。

大概过程:
创建两个表,OPEN, CLOSE。
OPEN表保存所有已生成而未考察的节点,CLOSED表中记录已访问过的节点。
1. 访问路网中里起始点最近且没有被检查过的点,把这个点放入OPEN组中等待检查。
2. 从OPEN表中找出距起始点最近的点,找出这个点的所有子节点,把这个点放到CLOSE表中。
3. 遍历考察这个点的子节点。求出这些子节点距起始点的距离值,放子节点到OPEN表中。
4. 重复2,3,步。直到OPEN表为空,或找到目标点。

在这里插入图片描述
这是在drew 程序中4000个节点的随机路网上Dijkstra算法搜索最短路的演示,黑色圆圈表示经过遍历计算过的点由图中可以看到Dijkstra算法从起始点开始向周围层层计算扩展,在计算大量节点后,到达目标点。所以速度慢效率低。

提高Dijkstra搜索速度的方法很多,据Drew所知,常用的有数据结构采用Binary heap的方法,和用Dijkstra从起始点和终点同时搜索的方法。

代码实现:

/*
测试数据 教科书 P189 G6 的邻接矩阵 其中 数字 1000000 代表无穷大
6
1000000 1000000 10 100000 30 100
1000000 1000000 5 1000000 1000000 1000000
1000000 1000000 1000000 50 1000000 1000000
1000000 1000000 1000000 1000000 1000000 10
1000000 1000000 1000000 20 1000000 60
1000000 1000000 1000000 1000000 1000000 1000000
结果:
D[0]   D[1]   D[2]   D[3]   D[4]   D[5]
 0   1000000   10     50     30     60
*/
#include <stdio.h>
#define MAX 1000000

int arcs[10][10];//邻接矩阵
int D[10];//保存最短路径长度
int p[10][10];//路径
int final[10];//若final[i] = 1则说明 顶点vi已在集合S中
int n = 0;//顶点个数
int v0 = 0;//源点
int v,w;
void ShortestPath_DIJ()
{
    for (v = 0; v < n; v++) //循环 初始化
    {
        final[v] = 0; D[v] = arcs[v0][v];
        for (w = 0; w < n; w++) p[v][w] = 0;//设空路径
        if (D[v] < MAX) {p[v][v0] = 1; p[v][v] = 1;}
    }
    D[v0] = 0; final[v0]=1; //初始化 v0顶点属于集合S
    //开始主循环 每次求得v0到某个顶点v的最短路径 并加v到集合S中
    for (int i = 1; i < n; i++)
    {
        int min = MAX;
        for (w = 0; w < n; w++)
        {
            //我认为的核心过程--选点
            if (!final[w]) //如果w顶点在V-S中
            {
                //这个过程最终选出的点 应该是选出当前V-S中与S有关联边
                //且权值最小的顶点 书上描述为 当前离V0最近的点
                if (D[w] < min) {v = w; min = D[w];}
            }
        }
        final[v] = 1; //选出该点后加入到合集S中
        for (w = 0; w < n; w++)//更新当前最短路径和距离
        {
            /*在此循环中 v为当前刚选入集合S中的点
               则以点V为中间点 考察 d0v+dvw 是否小于 D[w] 如果小于 则更新
               比如加进点 3 则若要考察 D[5] 是否要更新 就 判断 d(v0-v3) + d(v3-v5) 的和是否小于D[5]
               */
            if (!final[w] && (min+arcs[v][w]<D[w]))
            {
                D[w] = min + arcs[v][w];
                // p[w] = p[v];
                p[w][w] = 1; //p[w] = p[v] + [w]
            }
        }
    }
}


int main()
{
    freopen("./Dijkstra.txt", "r", stdin);
    scanf("%d", &n);
    for (int i = 0; i < n; i++)
    {
        for (int j = 0; j < n; j++)
        {
            scanf("%d", &arcs[i][j]);
        }
    }
    ShortestPath_DIJ();
    for (int i = 0; i < n; i++) printf("D[%d] = %d\n",i,D[i]);
    return 0;
}

单源Dijkstra
在这里插入图片描述

参考:
https://www.jianshu.com/p/ff6db00ad866

https://blog.csdn.net/lbperfect123/article/details/84281300

https://blog.csdn.net/yalishadaa/article/details/55827681

https://www.cnblogs.com/guxuanqing/p/9610780.html

https://blog.csdn.net/weixin_44574633/article/details/116599738?spm=1001.2101.3001.6650.11&utm_medium=distribute.pc_relevant.none-task-blog-2%7Edefault%7ECTRLIST%7Edefault-11.no_search_link&depth_1-utm_source=distribute.pc_relevant.none-task-blog-2%7Edefault%7ECTRLIST%7Edefault-11.no_search_link
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

Dijkstra算法图文详解 的相关文章

  • bs4遍历文档树,搜素文档树,find_all参数,selenium,模拟登陆百度

    这里写目录标题 一 昨日回顾二 今日内容1 bs4遍历文档树2 bs4的搜索文档树3 find all的其他参数4 css选择器5 selenium的介绍6 selenium的使用7 模拟登陆百度8 selenium的其他使用 一 昨日回顾
  • xpath的使用,selenium爬取京东商品信息,scrapy介绍,安装及使用

    这里写目录标题 一 xpath的使用二 selenium爬取京东商品信息三 scrapy的架构3 1scrapy的架构3 2目录介绍 四 scrapy的简单使用 一 xpath的使用 span class token number 1 sp
  • go语言值变量命名规范,定义变量,数据类型,常量,函数基础,函数高级

    这里写目录标题 一 昨日回顾二 今日内容1 变量命名规范2 变量代码演示 3 类型代码演示 4 常量5 函数基础6 函数高级 一 昨日回顾 span class token number 1 span redis高级 span class
  • 串口接收一帧数据及解析

    3 xff0e 下位机中的数据接收和协议解析 下位机接收数据也有两种方式 xff0c 一 等待接收 xff0c 处理器一直查询串口状态 xff0c 来判断是否接收到数据 二 中断接收 两种方法的优缺点在此前的一篇关于串口通信的文章中详细讨论
  • <string>库常用的函数

    include lt string h gt 库包含字符串处理函数 xff0c 常用的有strcpy strcat strcmp strchr等 1 strcpy是字符串赋值函数 char strcpy char target char s
  • APM(Ardupilot)——电机输出流程图

    电机类声明 xff1a system cpp void Copter allocate motors void switch AP Motors motor frame class g2 frame class get if FRAME C
  • C++中的三个特殊宏:__FILE__,__FUNCTION__和__LINE__

    C 43 43 中的三个特殊宏 xff1a FILE xff0c FUNCTION 和 LINE 1 FILE 宏 FILE 宏用于检查当前文件名 xff0c 例如 xff1a include lt cstdio gt using name
  • GD32F10x外部晶振配置108MHz系统时钟

    嵌入式 GD32F10x外部晶振配置108MHz系统时钟 文章目录 嵌入式 GD32F10x外部晶振配置108MHz系统时钟前言一 时钟树与配置思路二 时钟配置过程三 晶振故障排查总结 前言 由于公司更改硬件设计选择使用新的型号兆易创新国产
  • Keil MDK C (error: #29: expected an expression) 错误的解决

    今天 xff0c 自己建了一个EFM32工程模版 xff0c 调试代码时显示 App Panel main c 119 error 29 expected an expression 仔细的检查了半个小时 xff0c 最后解决了 xff01
  • HTTP协议之报文详解

    学习WEB开发需要对HTTP协议熟悉 xff0c 下面直接进入主题 一 什么是报文 报文 xff0c 是网络中交换和传输的数据单元 xff0c 即站点一次性要发送的数据块 报文包含了将要发送的完整的数据信息 xff0c 其长短很不一致 xf
  • linux发送tcp/udp请求

    本文章介绍下通过nc工具 iperf工具和python脚本 xff0c 实现发送tcp udp请求 一 nc工具 xff08 netcat工具 xff09 这个工具linux系统默认是自带的 xff0c 以下是命令的常用参数 1 1 发送t
  • 第一次网页前端培训笔记(HBuilderX)

    一 安装HBuilderX 官网 xff1a HBuilderX 高效极客技巧 dcloud io 二 了解HBuilderX lt DOCTYPE html gt lt html gt lt head gt lt meta charset
  • 第二次网页前端培训笔记(HBuilderX)

    常用标签 一 表单 form标签 xff1a 表单标签 xff0c 块级元素 xff0c 会自动换行 xff1b 将数据传输给服务器 常用属性 xff1a action 表单提交的地址url id 唯一标识 name 名称 target 表
  • 前端第7次培训

    对象 一对象的创建 1 字面量形式创建对象 var对象名 61 xff1b var对象名 61 键 xff1a 值 2 通过new Object创建 var对象名 61 new Object xff08 xff09 3 通过Object对象
  • MPU6050的再次深度学习与实操遇到问题

    数据的处理与实现 xff1a MPU6050芯片提供的数据夹杂有较严重的噪音 xff0c 在芯片处理静止状态时数据摆动都可能超过2 除了噪音 xff0c 各项数据还会有偏移的现象 xff0c 也就是说数据并不是围绕静止工作点摆动 xff0c
  • moderlarts第一次作业

    一 物体检测模型 以口罩检测为例 1 下载OBS 2 打开华为云 xff0c 找到modelarts控制台 xff0c 鼠标移到用户名上 xff0c 点击我的凭证 3 点击访问密钥 gt 新增访问密钥 xff0c 下载 xff0c 然后登陆
  • 培训modelarts 二

    一 进行声音分类 1 下载数据包 xff0c 导入OBS 2 创建声音分类项目 3 标签分类 4 开始训练 5 部署模型 6 预测结果 二 AI gallery 1 下载数据集 2 创建数据集 xff0c 导入外卖评论 3 进行创建文本分类
  • Jetson Xavier NX 配置(七)—— 数据传输之socket文件传输 & usb摄像头RTSP视频推流

    目录 1 Python socket 文件传输 xff08 1 xff09 发送单个文件 xff08 一次性 xff09 xff08 2 xff09 发送一个文件夹下的所有文件 xff08 一次性 xff09 xff08 3 xff09 发
  • 使用plist文件进行ipa的安装

    前提 将html 用户扫码 地址访问 ipa和plist放在https的远程服务器上 编写html文件 内容如下 lt DOCTYPE html PUBLIC W3C DTD XHTML 1 0 Transitional EN http w
  • 关于U盘变成RAW格式 windows无法格式化的解决方法

    网上有很多人说是U盘坏了 xff0c 其实不是这样 这个问题是可以解决的 xff0c 解决方法也是在网上搜索到的 xff0c 到这里同大家分享下 本人昨天使用U盘的时候就碰到了U盘变成RAW格式 xff0c 系统可以读出盘符 xff0c 但

随机推荐

  • Xcode11.6编写C++项目出现报错:vector or iostream file not found

    解决办法 xff1a
  • iPhone设备型号代码(iPhone 4s - iPhone 14)

    lt string gt iPhone15 3 lt string gt iPhone 14 Pro Max lt string gt iPhone15 2 lt string gt iPhone 14 Pro lt string gt i
  • [Linux] Vim 撤销 回退 操作

    在vi中按u可以撤销一次操作 u 撤销上一步的操作 Ctrl 43 r 恢复上一步被撤销的操作 注意 xff1a 如果你输入 u 两次 xff0c 你的文本恢复原样 xff0c 那应该是你的Vim被配置在Vi兼容模式了 重做 如果你撤销得太
  • 为什么系统进入到Checking Media Presence

    你按联想热启键来开机 xff0c 也就是那个还原键来开机 然后你选择BIOS Setup回车 选择Boot这项的boot mode把UEFI改成legacy support和boot priority把UEFI改成legacy 然后保存退出
  • MacBook Air响一声白屏故障情况说明及解决

    情况说明 xff1a 2013款的MacBook Air安装Windows 7系统 xff0c 结果导致开机响一声就白屏 xff0c 按option无选项出现 xff0c 其他各种组合按键尝试都无效 百度搜索 xff0c 有人说是屏幕故障
  • 如何在Eclipse中打开现有项目(高手免入)

    如果我们现在已经有了Java项目 xff08 网上下载的或者从别的电脑上拷贝过来的 xff09 xff0c 我们都知道 xff0c Eclipse和其他的编程软件不一样 xff0c 不能够通过直接双击某个文件的方式来打开 xff0c 那么我
  • svn is not a working copy 怎么解决

    确定当目录下是否含有 svn文件夹 如果没有就重新啊checkout xff0c 或者在上一层目录或下一层目录查找 xff0c 有则可执行 svn commit m 34 更新部分代码 34
  • CSS3设置Border边框是内边框还是外边框

    CSS3可以设置边框是向内还是向外 xff0c 如果要设置为内边框使用 1 box sizing border box 外边框 1 box sizing content box
  • If this view is optional add '@Nullable' (fields) or '@Optional' (methods) ...

    lt 在出错的activity中 xff0c 对应布局文件中加入 gt lt 不能缺少 xff0c 缺少后出现If this view is optional add 39 64 Nullable 39 fields or 39 64 Op
  • MTK Camera(OV13850) 驱动移植

    一 驱动源码包结构 拿到的驱动源码包解压后得到hal和kernel两个目录文件 xff0c 源码目录结构如下所示 13850 6592 driver 10 28 7z hal camera AE PLineTable ov13850mipi
  • 查看路由器WAN口IP是否为公网ip指南

    查看路由器WAN口IP是否为公网ip指南 吴捷 一 xff0e 公网ip和私网ip ip地址分类中常用的有A B C类 xff0c 每类IP中都规划了一段私网IP xff0c 除了这些私网外的IP都是公网IP 分类IP地址范围适用用户A1
  • [iOS] WKWebView 于JavaScript传值

    如果在项目中采用WKWebView的方法加载网页 OC向JS传值方法总结 xff1a 1 OC gt JS 传数组的方法 xff1a NSString arrStr 61 self arr componentsJoinedByString
  • iOS日历中的日程生成VCalendar 2.0(.vcs)格式的字符串和解析

    获取 VCalendar2 0 的格式字符串 43 NSString getVCalendar20StrWithEvents NSArray lt EKEvent gt events NSString vcalendar 61 NSStri
  • 数传电台术语详解

    数传电台 xff08 data radio xff09 是指借助DSP 技术和无线电技术实现的高性能专业数据传输电台 数传电台的使用从最早的按键电码 电报 模拟电台加无线MODEM xff0c 发展到目前的数字电台和DSP 软件无线电 xf
  • 无线数传电台的发展趋势

    摘自 专业无线通信 传媒 无线数传电台作为一种最简洁的通行方式 xff0c 具有很长的历史 xff0c 其基本的特征是通联方便 简捷 xff0c 同时也存在着封闭性强的特点 xff0c 正是由于上述原因 xff0c 无线数传电台产品的生命期
  • wget 提交post请求

    格式 xff1a wget post data 34 item1 61 value1 amp item2 61 value2 34 http xxx xxx com 示例 xff1a wget post data 34 username 6
  • 欧拉角、轴角与四元数

    1 欧拉角 欧拉角使用最简单的x y z值来分别表示在x xff0c y xff0c z轴上的旋转角度 xff0c 其取值为0 360 或者0 2pi xff09 xff0c 一般使用roll xff0c pitch xff0c yaw来表
  • Linux 系统投屏显示

    最近使用电脑跑Linux时需要用到显示器投屏 xff0c 于是快乐的拿上我的笔记本连上了投影仪 emmm 然鹅并没有什么卵用 果断问度娘 xff0c 看到好多人说使用xrandr命令设置 xff0c 于是便上手试了下 xff0c 看到我运行
  • C++ 判断一个 int 型整数是否为 2 的 N 次方(幂次)

    判断一个整数是否为2的幂次方法有以下几种 xff1a 1 循环除2 这是最简单最好理解的方式 对于一个数如果是2的幂次 xff0c 则其肯定可以被2一直整除直到其值为1 所以可以通过一个while循环判断 xff1a void judge
  • Dijkstra算法图文详解

    Dijkstra算法算是贪心思想实现的 xff0c 首先把起点到所有点的距离存下来找个最短的 xff0c 然后松弛一次再找出最短的 xff0c 所谓的松弛操作就是 xff0c 遍历一遍看通过刚刚找到的距离最短的点作为中转站会不会更近 xff