话不多说,先看图

1.1 朴素版的Dijkstra算法

一般用到这个情况稠密图,也就是节点的个数比边的个数少。 (稠密图用邻接矩阵存储)

#include<cstring>
#include<iostream>
#include<algorithm> using namespace std; const int N = 510; int n, m;
int g[N][N];//稠密图用邻接矩阵,g[a][b] 表示从a点到b点的距离
int dist[N];//用于存储每个店到起点的最小距离
bool st[N];//用于在更新最短距离时,判断当前点的最短距离是否确定,是否需要更新 int dijkstra(){ memset(dist, 0x3f, sizeof dist);//初始化距离, 0x3f代表无限大
dist[1] = 0;//第一个点到自身的距离时0 for(int i = 0; i < n; i++){//有n个点需要进行n次迭代 int t = -1; //t存储当前访问的点 for(int j=1; j<=n; j++) //这里的 j 代表从1号点开始
if(!st[j] && (t == -1 || dist[t] > dist[j])) //寻找未确定最短路径的点钟距离最短的点
t = j; for(int j = 1; j<=n; j++)
dist[j] = min(dist[j], dist[t] + g[t][j]); st[t] = true; } if(dist[n] == 0x3f3f3f3f) return -1;
return dist[n];
} int main(){
scanf("%d%d", &n, &m); memset(g, 0x3f, sizeof g);//初始化距离 while(m--){
int a, b, c;
scanf("%d%d%d", &a, &b, &c); g[a][b] = min(g[a][b], c);//和之前a点到b点的最小距离进行比较,取两个中的最小值
} printf("%d\n", dijkstra()); return 0;
}

2.2 堆优化版的Dijkstra算法

用到这种情况的是稀疏图。 (点多边的数目少)

思路:

1 号点为例,判断一下1号点到源点的最短距离是不是已经确定了, 如果已经确定了, 跳出本次循环。如果还没有确定,厕把他的 st[1] = true , 这里思考一下我们为什么把1号点的状态改为 true, 因为所有指向1 号点的点最短距离已经确定, 自然 1 号点的最短距离也就确定了, 接下来遍历一下1号点所有指向的点 更新 1 号点指向的点的最短距离 ,

#include<cstring>
#include<iostream>
#include<algorithm>
#include<queue> using namespace std; typedef pair<int, int> PII; const int N = 1e6 + 10; int n, m;
int h[N], w[N], e[N], ne[N], idx;
int dist[N];
bool st[N]; void add(int a, int b, int c)
{
e[idx] = b, w[idx] = c, ne[idx] = h[a], h[a] = idx++;
} int dijkstra(){
memset(dist, 0x3f, sizeof dist); 初始化所有点到源点的距离为 无穷大
dist[1] = 0; // 1 号点就是源点, 所有到自身的距离是 0
priority_queue<PII, vector<PII>, greater<PII>> heap; //小根堆
heap.push({0, 1}); // 距离源点最近的点入堆 while(heap.size()) // 堆不空
{
auto t = heap.top();
heap.pop(); int var = t.second; //取到 还没有确定到源点的最短距离的点中 到源点距离最近的点 if(st[var]) continue; //判断一下该点到源点的距离是否已经确定, 如果确定跳出本次循环
st[var] = true; for(int i = h[var]; i != -1; i = ne[i])//遍历一下var 所有指向的点
{
int j = e[i];
if(dist[j] > dist[var] + w[i])
{
dist[j] = dist[var] + w[i];
heap.push({dist[j], j});
}
}
} if(dist[n] == 0x3f3f3f3f) return -1;
return dist[n];
} int main(){
scanf("%d%d", &n, &m); memset(h, -1, sizeof h); while(m--){
int a, b, c;
scanf("%d%d%d", &a, &b, &c);
add(a, b, c);
} printf("%d\n", dijkstra()); return 0;
}

用 Dijkstra 算法解决最短路问题的更多相关文章

  1. dijkstra算法解决单源最短路问题

    简介 最近这段时间刚好做了最短路问题的算法报告,因此对dijkstra算法也有了更深的理解,下面和大家分享一下我的学习过程. 前言 呃呃呃,听起来也没那么难,其实,真的没那么难,只要弄清楚思路就很容易 ...

  2. Dijkstra算法解决单源最短路径

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

  3. 图论(四)------非负权有向图的单源最短路径问题,Dijkstra算法

    Dijkstra算法解决了有向图G=(V,E)上带权的单源最短路径问题,但要求所有边的权值非负. Dijkstra算法是贪婪算法的一个很好的例子.设置一顶点集合S,从源点s到集合中的顶点的最终最短路径 ...

  4. 【算法导论】单源最短路径之Dijkstra算法

    Dijkstra算法解决了有向图上带正权值的单源最短路径问题,其运行时间要比Bellman-Ford算法低,但适用范围比Bellman-Ford算法窄. 迪杰斯特拉提出的按路径长度递增次序来产生源点到 ...

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

    对于网图来说,最短路径,是指两顶点之间经过的边上权值之和最少的路径,并且我们称路径上的第一个顶点为源点,最后一个顶点为终点.最短路径的算法主要有迪杰斯特拉(Dijkstra)算法和弗洛伊德(Floyd ...

  6. 最短路径-迪杰斯特拉(dijkstra)算法及优化详解

    简介: dijkstra算法解决图论中源点到任意一点的最短路径. 算法思想: 算法特点: dijkstra算法解决赋权有向图或者无向图的单源最短路径问题,算法最终得到一个最短路径树.该算法常用于路由算 ...

  7. 最短路径算法 2.Dijkstra算法

    Dijkstra 算法解决的是带权重的有向图上单源最短路径问题,该算法要求所有边的权重都为非负值.该算法的时间复杂度是O(N2),相比于处理无负权的图时,比Bellmad-Ford算法效率更高. 算法 ...

  8. [最短路径问题]Dijkstra算法(含还原具体路径)

    前言 在本篇文章中,我将介绍 Dijkstra 算法解决 单源最短路径问题 ,同时还包含了具体路径的还原.以下是我自己的全部学习过程与思考,参考书籍为 <数据结构>(C++语言版) 邓俊辉 ...

  9. 最短路问题---Dijkstra算法学习

    Dijkstra又称单源最短路算法,就从一个节点到其他各点的最短路,解决的是有向图的最短路问题 此算法的特点是:从起始点为中心点向外层层扩展,直到扩展到中终点为止. 该算法的条件是所给图的所有边的权值 ...

  10. 最短路问题Dijkstra算法

    Dijkstra算法可以解决源点到任意点的最短距离并输出最短路径 准备: 建立一个距离数组d[ n ],记录每个点到源点的距离是多少 建立一个访问数组v[ n ],记录每个点是否被访问到 建立一个祖先 ...

随机推荐

  1. 关于VS2022使用EF生成实体模型报错的问题:运行转换:System.NullReferenceException:对象引用未设置为对象的示例。

    起因: 之前版本vs2022生成EF模型一直没有问题,在更新了最新的vs2022之后,版本号17.6+,出现此问题: 运行转换:System.NullReferenceException:对象引用未设 ...

  2. SpringBoot定义优雅全局统一Restful API 响应框架六

    闲话不多说,继续优化 全局统一Restful API 响应框架 做到项目通用 接口可扩展. 如果没有看前面几篇文章请先看前面几篇 SpringBoot定义优雅全局统一Restful API 响应框架 ...

  3. 稳,从数据库连接池 testOnBorrow 看架构设计

    本文从 Commons DBCP testOnBorrow 的作用机制着手,管中窥豹,从一点去分析数据库连接池获取的过程以及架构分层设计. 以下内容会按照每层的作用,贯穿分析整个调用流程. 1️⃣框架 ...

  4. Linux系统运维之Web服务器Nginx安装

    一.介绍 Nginx是一款轻量级的Web 服务器/反向代理服务器及电子邮件(IMAP/POP3)代理服务器,并在一个BSD-like 协议下发行.本文先整理web服务器内容. 二.环境及软件版本 操作 ...

  5. PostgreSQL 12 文档: 部分 VI. 参考

    部分 VI. 参考 这份参考中的条目意欲提供关于相应主题的权威.完整和正式的总结.关于使用PostgreSQL的更多信息(以叙述.教程或例子的形式)可以在本书的其他部分找到.见每个参考页面上列出的交叉 ...

  6. 【.Net/C#之ChatGPT开发系列】四、ChatGPT多KEY动态轮询,自动删除无效KEY

    ChatGPT是一种基于Token数量计费的语言模型,它可以生成高质量的文本.然而,每个新账号只有一个有限的初始配额,用完后就需要付费才能继续使用.为此,我们可能存在使用多KEY的情况,并在每个KEY ...

  7. Stable Diffusion生成图片的参数查看与抹除方法

    前几天分享了几张Stable Diffusion生成的艺术二维码,有同学反映不知道怎么查看图片的参数信息,还有的同学问怎么保护自己的图片生成参数不会泄露,这篇文章就来专门分享如何查看和抹除图片的参数. ...

  8. Python 潮流周刊第 11 期(2023-07-15)

    查看全文:Python潮流周刊#11:如何使用 Golang 运行 Python 代码? 文章&教程 1.使用 Golang 和 Docker 运行 Python 代码 2.答案在代码中:&q ...

  9. Appium新版本引发的一个问题

    Appium新版本引发的一个问题 准备工作 测试代码 from appium import webdriver des_cap = {'platformName': 'android'} driver ...

  10. 2021-7-12 VUE的增删改查功能简单运用

    Vue增删改查简易实例 <!DOCTYPE html> <html> <head> <title> </title> <style t ...