有关最短路径的最后一个算法——Dijkstra

迪杰斯特拉算法是由荷兰计算机科学家迪杰斯特拉于1959 年提出的,因此又叫迪杰斯特拉算法。是从一个顶点到其余各顶点的最短路径算法,解决的是有权图中最短路径问题。迪杰斯特拉算法主要特点是以起始点为中心向外层层扩展,直到扩展到终点为止。

本蒟蒻认为这个是最为重要的一个有关最短路径的算法

  Dijkstra使用了广度优先搜索解决赋权有向图或者无向图的单源最短路径问题,算法最终得到一个最短路径树。该算法常用于路由算法或者作为其他图算法的一个子模块。

  它的主要特点是以起始点为中心向外层层扩展(广度优先搜索思想),直到扩展到终点为止。

  它主要采用的是一种贪心的策略,声明一个数组dis来保存源点到各个顶点的最短距离和一个保存已经找到了最短路径的顶点的集合:T,初始时,原点 s 的路径权重被赋为 0 (dis[s] = 0)。若对于顶点 s 存在能直接到达的边(s,m),则把dis[m]设为w(s, m),同时把所有其他(s不能直接到达的)顶点的路径长度设为无穷大。初始时,集合T只有顶点s。
然后,从dis数组选择最小值,则该值就是源点s到该值对应的顶点的最短路径,并且把该点加入到T中,OK,此时完成一个顶点,
  然后,我们需要看看新加入的顶点是否可以到达其他顶点并且看看通过该顶点到达其他点的路径长度是否比源点直接到达短,如果是,那么就替换这些顶点在dis中的值。
  最后,又从dis中找出最小值,重复上述动作,直到T中包含了图的所有顶点。

下面用以为大佬的图来举个例子

首先是相对来说较容易理解的代码

#include<bits/stdc++.h>
using namespace std;
inline int read()
{
int X=,w=;
char c=getchar();
while(c<''||c>'')
{
if (c=='-')
{
w=-;
c=getchar();
}
}
while(c>=''&&c<='')
{
X=(X<<)+(X<<)+c-'';
c=getchar();
}
return X*w;
}
const int maxn=;
int g[maxn][maxn];//g数组用来存储图;
int n,m,s;//分别表示点的个数、有向边的个数、出发点的编号;
bool vis[maxn];//表示是否已经到达过;
int d[maxn];//d[i]表示从询问点到点i的最短路径;
const int inf=;
int main ()
{
n=read(),m=read(),s=read();
for(int i=;i<=n;i++)
{
d[i]=inf;
for(int j=;j<=n;j++)
g[i][j]=inf;
g[i][i]=;//自己到自己的最短路径当然是0
}//初始化数组;
for(int i=;i<=m;i++)
{
int u=read(),v=read(),w=read();
//u,v,i分别表示第i条有向边的出发点、目标点和长度;
g[u][v]=w;//读入;
}
vis[s]=;//将起点标记成已经到达;
for(int i=;i<=n;i++)
d[i]=g[s][i];//将最短路径初始化;
//如果两点之间有路线就初始化为该距离,如果没有就还是inf;
while()
{
int stt_node=,stt_dis=inf;//stt=shortest 初始化两个变量
// stt_node表示最短路径的终点,stt_dis表示最短路径的长度
for(int i=;i<=n;i++)
{
if(vis[i]==&&d[i]<stt_dis)
//如果该点还没有到达,并且他的距离小于最短距离
{
stt_node=i,stt_dis=d[i];//更新变量
}
}
if(stt_node==) break;
//如果已经没有可以更新的最短路径了,就说明已经结束了
vis[stt_node]=;//将该点标记成已经到达
for(int i=;i<=n;i++)
{
if(vis[i]||g[stt_node][i]==inf)continue;
//如果并没有到达或者是两点之间没有路径,就跳出循环
d[i]=min(d[i],stt_dis+g[stt_node][i]);//更新最短路径
}
}
for(int i=;i<=n;i++)
printf("%d ",d[i]);
return ;
}

下面便是代码实现了qwq:

#include<bits/stdc++.h>
using namespace std;
int n,m;
const int nmax=,mmax=;
int fir[nmax],to[mmax],nxt[mmax],dis[mmax],ecnt;
void add(int u,int v,int w)
{
to[++ecnt]=v;
dis[ecnt]=w;
nxt[ecnt]=fir[u];
fir[u]=ecnt;
}
struct node
{
int x,d;
node(int x,int d):x(x),d(d){}
};
bool operator<(node a,node b)
{
return a.d>b.d;
}
int d[nmax];
bool vis[nmax];
void dijkstra(int s)
{
memset(vis,,sizeof(vis));
memset(d,-,sizeof(d));
priority_queue<node>q;
q.push(node(s,));
d[s]=;
while(!q.empty())
{
node h=q.top();
q.pop();
if(vis[h.x])continue;
vis[h.x]=;
for(int e=fir[h.x];e;e=nxt[e])
{
if(vis[to[e]])continue;
if(d[to[e]]==-)
{
d[to[e]]=h.d+dis[e];
}
else
{
d[to[e]]=min(d[to[e]],h.d+dis[e]);
}
vis[to[e]]=;
q.push(node(to[e],d[to[e]]));
}
}
}
int main()
{
cin>>n>>m;
for(int i=;i<=m;i++)
{
int u,v,w;
cin>>u>>v>>w;
add(u,v,w);
add(v,u,w);
}
dijkstra();
for(int i=;i<=n;i++)
{
cout<<d[i]<<' ';
}
}

Dijkstra【迪杰斯特拉算法】的更多相关文章

  1. c/c++ 图的最短路径 Dijkstra(迪杰斯特拉)算法

    c/c++ 图的最短路径 Dijkstra(迪杰斯特拉)算法 图的最短路径的概念: 一位旅客要从城市A到城市B,他希望选择一条途中中转次数最少的路线.假设途中每一站都需要换车,则这个问题反映到图上就是 ...

  2. 图解Dijkstra(迪杰斯特拉)算法+代码实现

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

  3. (Dijkstra)迪杰斯特拉算法-最短路径算法

    迪杰斯特拉算法是从一个顶点到其余各顶点的最短路径算法,解决的是有向图中最短路径问题.迪杰斯特拉算法主要特点是以起始点为中心向外层层扩展,直到扩展到终点为止. 算法思想:设G=(V,E)是一个带权有向图 ...

  4. Dijkstra(迪杰斯特拉)算法求解最短路径

    过程 首先需要记录每个点到原点的距离,这个距离会在每一轮遍历的过程中刷新.每一个节点到原点的最短路径是其上一个节点(前驱节点)到原点的最短路径加上前驱节点到该节点的距离.以这个原则,经过N轮计算就能得 ...

  5. C# 迪杰斯特拉算法 Dijkstra

    什么也不想说,现在直接上封装的方法: using System; using System.Collections.Concurrent; using System.Collections.Gener ...

  6. 最短路径算法—Dijkstra(迪杰斯特拉)算法分析与实现(C/C++)

    Dijkstra算法 ———————————最后更新时间:2011.9.25———————————Dijkstra(迪杰斯特拉)算法是典型的最短路径路由算法,用于计算一个节点到其他所有节点的最短路径. ...

  7. 图->最短路径->单源最短路径(迪杰斯特拉算法Dijkstra)

    文字描述 引言:如下图一个交通系统,从A城到B城,有些旅客可能关心途中中转次数最少的路线,有些旅客更关心的是节省交通费用,而对于司机,里程和速度则是更感兴趣的信息.上面这些问题,都可以转化为求图中,两 ...

  8. 最短路问题:迪杰斯特拉算法(Dijsktra)

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

  9. 最短路之Dijkstra(迪杰斯特拉)

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

随机推荐

  1. 前端面试知识点集锦(JavaScript篇)

    目录 1.谈谈你对Ajax的理解?(概念.特点.作用) 2.说说你对延迟对象deferred的理解? 3.什么是跨域,如何实现跨域访问? 4.为什么要使用模板引擎? 5.JavaScript是一门什么 ...

  2. Gulp 前端优化

    使用方法: 下载 node.js , https://nodejs.org/en/,并安装 msi 一下命令都属于 dos 命令 node -v,npm -v,检验是否下载成功(出现版本号) 将 np ...

  3. web服务器负载均衡与集群基本概念二

    前面已经说过负载均衡的作用是在多个节点之间按照一定的策略(算法)分发网络或计算处理负载.负载均衡可以采用软件和硬件来实现.一般的框架结构可以参考下图.    后台的多个Web节点上面有相同的Web应用 ...

  4. 时空地图TimeGIS.com生成正交曲线网格

    数值模拟中对数学物理方程的求解过程中经常需要生成网格,这里提供了一种方便的方法,只需要简单地勾画出区域的轮廓, 就可以生成相应的正交曲线网格,详情请访问 www.TimeGIS.com

  5. 生鲜配送管理系统_升鲜宝V2.0 价格组功能 操作说明_15382353715

    价格组功能是B端供应链系统,必不可少的一个功能,其主要实现不同的客户不同的价格,B端系统有一个最大的不同就是,有些商品后台下单人员能看到的.有些商品在销售的那一瞬间,还不知道价格.所以这些商品只有后台 ...

  6. 测者的测试技术手册:Junit执行单元测试用例成功,mvn test却失败的问题和解决方法

    今天遇见了一个奇怪的问题,在IDE中run unit test,全部cases都成功了,但是后来通过mvn test运行case确保错了.在寻求原因的同时也找到了对应的解决方法. Run Unit T ...

  7. 前端开发之基础知识-HTML(二)

    1.6 html链接 html链接 <a>标签可以在网页上定义一个链接地址,通过src属性定义跳转的地址,通过title属性定义鼠标悬停时弹出的提示文字框. <a href=&quo ...

  8. hbase 工作原理

    一.HBASE介绍HBase是一个高可靠性.高性能.面向列.可伸缩的分布式存储系统,利用HBase技术可在廉价PC Server上搭建大规模结构化的存储集群.HBase的目标是存储并处理大型数据,具体 ...

  9. July 12th, 2018. Thursday, Week 28th.

    People love what other people are passionate about. 人总是会爱上别人倾注热情的事物. From La La Land. This quote has ...

  10. PHP设计模式概述

    PHP设计模式概述 设计模式(Design pattern)是一套被反复使用.多数人知晓的.经过分类编目的.代码设计经验的总结.使用设计模式是为了可重用代码.让代码更容易被他人理解.保证代码可靠性. ...