最短路径问题

看了王道的视频,感觉云里雾里的,所以写这个博客来加深理解。(希望能在12点以前写完)

floyd算法链接在底部,也可以直接点击这个超连接

一、总体思想

dijkstra算法的主要思想就是基于贪心,找出从v开始的顶点到各个点的最短路径,做法入下

1.初始化三个辅助数组

s[],dist[],path[]

s[]:这个数组用来标记结点的访问与否,如果该结点被访问,则为1,如果该结点还没有访问,则为0;

dist[]:这个数组用来记录当前从v到各个顶点的最短路径长度,算法的核心思想就是通过不断修改这个表实现;

path[]:这个数组用来存放最短路径;

2.遍历图,修改上面的各项数组,每次只找最短路径,直到遍历结束

二、代码实现

 void dijkstra(Graph G, int v)
{
int s[G.vexnum];
int dist[G.vexnum];
int path[G.vexnum];
for(int i = ; i < G.vexnum; i++)
{
s[i] = ;
dist[i] = G.edge[v][i];
if(G.edge[v][i] == max || G.edge[v][i] == )
{
path[i] = -;
}
else
{
path[i] = v;
}
s[v] = ;
} for(int i = ; i < G.vexnum; i++)
{
int min = max;
int u;
for(int j = ; j < G.vexnum; j++)
{
if(s[j] != && dist[j] < min)
{
min = dist[j];
u = j;
}
}
s[u] = ;
for(int j = ; j < G.vexnum; j++)
{
if(s[j] != && dist[j] > dist[u] + G.edge[u][j])
{
dist[j] = dist[u] + G.edge[u][j];
path[j] = u;
}
}
}
}

三、代码解释

先自己定义一个无穷大的值max

#define max inf

dijkstra算法传入的两个参为

图Graph G;

起点结点 int v;

首先我们需要三个辅助数组

 int s[G.vexnum];//记录结点时是否被访问过,访问过为1, 没有访问过为0
int dist[G.vexnum];//记录当前的从v结点开始到各个结点的最短路径长度
int path[G.vexnum];//记录最短路径,存放的是该结点的上一个为最短路径的前驱结点

初始化三个数组

 for(int i = ; i < G.vexnum; i++)
{
s[i] = ;//目前每个结点均未被访问过,设为0
dist[i] = G.edge[v][i];//dist[]数组记录每个从v结点开到其他i结点边的长度(权值)
if(G.edge[v][i] == max || G.edge[v][i] == )
{
path[i] = -;
}//如果v到i不存在路径或者i就是v结点时,将path[i]设为-1,意为目前v结点不存在路径到i
else
{
path[i] = v;
}//反之,若v到i存在路径,则v就是i的前驱结点,将path[i] = v
s[v] = ;//从遍历起点v开始,即已经访问过顶点s[v]=1
}

开始遍历数组并且每次修改辅助数组以记录目前的情况,直至遍历结束

 for(int i = ; i < G.vexnum; i++)
{
int min = max;//声明一个min = max用来每次记录这次遍历找到的最短路径的长度(权值)
int u;//声明u来记录这次历找到的最短路径的结点
for(int j = ; j < G.vexnum; j++)//开始遍历 找目前的最短路径
{
if(s[j] != && dist[j] < min)
{
min = dist[j];
u = j;
}//找出v到结点j的最短路径,并且记录下最短路径的结点u = j
}
s[u] = ;//找到结点u,即已访问过u,s[u] = 1
for(int j = ; j < G.vexnum; j++)//开始遍历 修改辅助数组的值
{
if(s[j] != && dist[j] > dist[u] + G.edge[u][j])
{
dist[j] = dist[u] + G.edge[u][j];
path[j] = u;
}//如果v→j的路径比v →u→j长,那么修改dist[j]的值为 dist[u] + G.edge[u][j],并且修改j的前驱结点为path[j] = u
}
}

遍历结束后,数组dist[]就是存放了起点v开始到各个顶点的最短路径长度

最短路径包含的结点就在path数组中

例如我们得到如下的path[]数组

 path[] = -;//0到自己无前驱结点
path[] = ;//1的前驱为结点0,0无前驱结点,即最短路径为0 →1
path[] = ;//2的前驱结为点1,1的前驱结点0,0无前驱结点,即最短路径为0 →1 →2
path[] = ;//3的前驱为结点0,0无前驱结点,即最短路径为0 →3
path[] = ;//4的前驱结为点2,2的前驱结为点1,1的前驱结点0,0无前驱结点,即最短路径为0 →1 →2 →4

其实不难看出,每次都会标记已经访问过的节点,访问过的节点不会再更改,即 这样的算法不可逆,也就是dijkstra对于存在负权值的图不适用,明天再更新Floyd算法叭

最短路径——dijkstra算法代码(c语言)的更多相关文章

  1. 最短路径-Dijkstra算法与Floyd算法

    一.最短路径 ①在非网图中,最短路径是指两顶点之间经历的边数最少的路径. AE:1    ADE:2   ADCE:3   ABCE:3 ②在网图中,最短路径是指两顶点之间经历的边上权值之和最短的路径 ...

  2. 最短路径——Dijkstra算法以及二叉堆优化(含证明)

    一般最短路径算法习惯性的分为两种:单源最短路径算法和全顶点之间最短路径.前者是计算出从一个点出发,到达所有其余可到达顶点的距离.后者是计算出图中所有点之间的路径距离. 单源最短路径 Dijkstra算 ...

  3. 网络最短路径Dijkstra算法

    最近在学习算法,看到有人写过的这样一个算法,我决定摘抄过来作为我的学习笔记: <span style="font-size:18px;">/* * File: shor ...

  4. 带你找到五一最省的旅游路线【dijkstra算法代码实现】

    算法推导过程参见[dijkstra算法推导详解] 此文为[dijkstra算法代码实现] https://www.cnblogs.com/Halburt/p/10767389.html package ...

  5. 单源最短路径Dijkstra算法,多源最短路径Floyd算法

    1.单源最短路径 (1)无权图的单源最短路径 /*无权单源最短路径*/ void UnWeighted(LGraph Graph, Vertex S) { std::queue<Vertex&g ...

  6. 数据结构实验之图论七:驴友计划 ( 最短路径 Dijkstra 算法 )

    数据结构实验之图论七:驴友计划 Time Limit: 1000 ms           Memory Limit: 65536 KiB Submit Statistic Discuss Probl ...

  7. 有向网络(带权的有向图)的最短路径Dijkstra算法

    什么是最短路径? 单源最短路径(所谓单源最短路径就是只指定一个顶点,最短路径是指其他顶点和这个顶点之间的路径的权值的最小值) 什么是最短路径问题? 给定一带权图,图中每条边的权值是非负的,代表着两顶点 ...

  8. Python数据结构与算法之图的最短路径(Dijkstra算法)完整实例

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

  9. 单源最短路径 dijkstra算法实现

    本文记录一下dijkstra算法的实现,图用邻接矩阵表示,假设图为无向图.而且连通,有向图,不连通图的做法相似. 算法简述: 首先确定"单源"的源.假设是第0个顶点. 维护三个数组 ...

随机推荐

  1. 【一起学设计模式】观察者模式实战:真实项目中屡试不爽的瓜娃EventBus到底如何实现观察者模式的?

    申明 本文章首发自本人公众号:壹枝花算不算浪漫,如若转载请标明来源! 感兴趣的小伙伴可关注个人公众号:壹枝花算不算浪漫 22.jpg 前言 之前出过一个设计模式的系列文章,这些文章和其他讲设计模式的文 ...

  2. 小白必看,Python 各种下划线都是啥意思_、_xx、xx_、__xx、__xx__、_classname_

    我们在定义一些变量或者方法的时候,常常会用到下划线,在 Python 中,下划线可是很有用处的哟,比如变量,有些是一个下划线开头的(_xx),有些是两个下划线开头的(__xx),有些是在名称的结尾添加 ...

  3. Jest 前端单元测试工具

    Jest和enzyme 前端单元测试工具 什么是Jest? Jest是一个令人愉悦的JavaScript测试框架,其重点是简单性. 它适用于使用以下项目的项目:Babel,TypeScript,Nod ...

  4. 2019-2020-1 20199325《Linux内核原理与分析》第七周作业

    第七周作业 1.进程描述符task_struct数据结构(一) 为了管理进程,内核必须对每个进程进行清晰的描述,进程描述符提供了内核所需了解的进程信息. struct task_struct数据结构很 ...

  5. java中ThreadLocal的使用

    文章目录 在Map中存储用户数据 在ThreadLocal中存储用户数据 java中ThreadLocal的使用 ThreadLocal主要用来为当前线程存储数据,这个数据只有当前线程可以访问. 在定 ...

  6. 云时代 • 新契机:2017届中国SaaS产业大会圆满落幕

    2017年5-6日,由拓普会展携手中国云体系产业创新战略联盟主办,江苏省企业信息化协会,浙江省企业信息化促进会,广东省首席信息官协会,CIO时代学院,IDC点评网协办以及上海市网购商会,中国信息化推进 ...

  7. 【STM32 .Net MF开发板学习-05】PC通过Modbus协议远程操控开发板

    从2002年就开始接触Modbus协议,以后陆续在PLC.DOS.Windows..Net Micro Framework等系统中使用了该协议,在我以前写的一篇博文中详细记载了这一段经历,有兴趣的朋友 ...

  8. ServerVariables集合

    当讨论Request对象内容时,要研究的集合之一就是ServerVariables集合.这个集合包含了两种值的结合体,一种是随同页面请求从客户端发送到服务器的HTTP报头中的值,另外一种是由服务器在接 ...

  9. 实战-MySQL定时增量备份(2)

    概要 引言 增量备份 恢复增量备份 定时备份 引言 在产品上线之后,我们的数据是相当重要的,容不得半点闪失,应该做好万全的准备,搞不好哪一天被黑客入侵或者恶意删除,那就 gg 了.所以要对我们的线上数 ...

  10. Blockchain

    一.中心化 中心化原则是我们日常比较常见的支付手段. 科普文章喜欢用网购举例: 1.你在某宝支付了一件商品,钱先到马云爸爸手中,通知商家发货: 2.商家发货,你收货后确认无误,点击确认收货: 3.马云 ...