当前位置: 首页 > news >正文

图论 之 迪斯科特拉算法求解最短路径

文章目录

  • 题目
    • 743.网络延迟时间
    • 3341.到达最后一个房间的最少时间I

求解最短路径的问题,分为使用BFS和使用迪斯科特拉算法,这两种算法求解的范围是有区别的

  • BFS适合求解,边的权值都是1的图中的最短路径的问题
    图论 之 BFS
  • 迪斯科特拉算法适合求解边的权值不一样的图,其中,该算法有两种实现方式,分别适用于两种情况的图
    • 稠密图,使用朴素的Dijkstra算法,其中稠密图的定义是,边的数量级与 o ( n 2 ) o(n^2) o(n2)相当的图,朴素的Dijkstra算法的时间复杂度是 o ( n 2 ) o(n^2) o(n2),其中n是图的节点的数量
    • 稀疏图,使用堆优化的Dijkstra算法,算法的时间复杂度是 o ( m l o g m ) o(mlogm) o(mlogm)其中,m是边的数量,如果输入的稠密图,那么使用堆优化的Dijkstra算法的时间复杂度是 o ( n 2 l o g n ) o(n^2logn) o(n2logn)

朴素的Dijkstras算法的模版

# 存储边的情况
edge = [[float('inf')]*n for n in range(n)]
# dis[i]表示 单源点k到其余节点i的最短的路径
dis = [float('inf')]*n 
dis[k] = 0
# 这个done[k] = True不用设置,后面会依据这个,把起点弹出
done = [False]*n # done[i]标记是否找到 到达节点i的最短的路径while True:x = -1for i,ok in enumerate(done):# 找到在还没确定最小距离的节点,该节点到源点的距离最小if not ok and (x < 0 or dis[i] < dis[x]):x = i# 判断是否都找到了if x < 0:# 这里就已经求解完成了,后续你可以返回最大值?return dis# 有节点无法到达if dis[x] == float('inf'):return -1# 设置标志位,表示节点x的最小距离已经确定done[x] = True# 遍历当前节点的所有的邻居,更新答案for j,d in enumerate(edge[x]):dis[j] = min(dis[j],dis[j]+d)

使用堆优化的Dijkstra算法


import heapqclass Solution:def networkDelayTime(self, times: List[List[int]], n: int, k: int) -> int:# 使用堆优化的Dijkstra算法# 使用堆优化的话,适用于稀疏图,所以边的记录,我们使用邻接表edge = [[] for _ in range(n)]for x,y,z in times:edge[x-1].append((y-1,z))dis = [float('inf')]*n dis[k-1] = 0# 入堆的元素是 (dis[x],x),第一个元素是距离,这也是设置的优先级h = [(0,k-1)]while h:# 出堆dx,x = heapq.heappop(h)# 如果当前的距离大于最小距离,直接过if dx > dis[x]:# 说明之前出过堆continue# 访问邻居,不一定是这个邻接表或者邻接矩阵,二维表也可以for y,d in edge[x]:# 计算更新值,计算方式按照题目的意思new_dis = dx + d # 只有更优的值才能被加入进去if new_dis < dis[y]:dis[y] = new_disheapq.heappush(h,(new_dis,y))mx = max(dis)return mx if mx < float('inf') else -1

题目

743.网络延迟时间

743.网络延迟时间

在这里插入图片描述

在这里插入图片描述

思路分析:由于边的数量远远大于节点的数量,所以我们还是考虑使用稠密图下的朴素的Dijkstra算法,最后返回不是无穷的最大的路径即可

class Solution:def networkDelayTime(self, times: List[List[int]], n: int, k: int) -> int:# 区别于BFS求解的最短距离,这个距离的边的权值不一样# 使用朴素的迪斯科特拉算法# 邻接矩阵记录边的情况edge = [[float('inf')]*(n) for _ in range(n)]# 有向边for e in times:edge[e[0]-1][e[1]-1] = e[2]dis = [float('inf')]*n # 记录k到各个节点的最短距离ans = dis[k-1] = 0done = [False] * n # 记录节点的最短距离是否被确定while True:x = -1# 找到最短距离还没确定,并且节点k到它的距离是最短的节点for i,ok in enumerate(done):if not ok and (x<0 or dis[i] < dis[x]):x = i # 如果x<0,表示全部的节点已经全部都访问过了if x < 0 :return ans# 如果最短的节点的距离是无穷,说明不可达if dis[x] == float('inf'):return -1# 更新ans = dis[x]done[x] = Truefor y,d in enumerate(edge[x]):dis[y] = min(dis[y],dis[x]+d)

使用堆优化的解法

import heapqclass Solution:def networkDelayTime(self, times: List[List[int]], n: int, k: int) -> int:# 使用堆优化的Dijkstra算法# 使用堆优化的话,适用于稀疏图,所以边的记录,我们使用邻接表edge = [[] for _ in range(n)]for x,y,z in times:edge[x-1].append((y-1,z))dis = [float('inf')]*n dis[k-1] = 0# 入堆的元素是 (dis[x],x)h = [(0,k-1)]while h:dx,x = heapq.heappop(h)if dx > dis[x]:# 说明之前出过堆continuefor y,d in edge[x]:new_dis = dx + d if new_dis < dis[y]:dis[y] = new_disheapq.heappush(h,(new_dis,y))mx = max(dis)return mx if mx < float('inf') else -1

3341.到达最后一个房间的最少时间I

3341.到达最后一个房间的最少时间I

在这里插入图片描述

思路分析:开始的时候,我错误的以为题目中只能向右或者向下运动, 所以写了一个动态规划进行求解,实际上,这个思路是错误的,不过要是只能向下或者向右运动的话,动态规划也是一种很好的做法

# 动态规划的做法,竟然可以过700个测试用例
import heapq
class Solution:def minTimeToReach(self, moveTime: List[List[int]]) -> int:# 开始的时候从(0,0)出发,移动到相邻的房间,其实也只是向下或向右运动# 感觉可以用动态规划,dp[i][j]表示到达i,j所需的最少的时间# 递推公式,# dp[i][j] = min(max(dp[i-1][j],moveTime[i][j])+1,max(dp[i][j-1],moveTime[i][j])+1)n = len(moveTime)m = len(moveTime[0])dp = [[float('inf')]*(m+1) for _ in range(n+1)]dp[1][1] = 0for i in range(n):for j in range(m):if i == 0 and j == 0:continuedp[i+1][j+1] = min(max(dp[i][j+1],moveTime[i][j])+1,max(dp[i+1][j],moveTime[i][j])+1)for i in dp:print(i )return dp[n][m]

正确的思路:应该是使用Dijkstra算法,不过开始的时候,我有点纠结这个edge也就是边的矩阵如何转化为邻接矩阵或者邻接表,后面一想,还是我的固定思维阻碍了我,邻接矩阵和邻接表只是一个工具,帮助我们找到当前的节点的邻居,但是在现在的图中,你通过坐标的加减不就可以得到对应的邻居嘛!

  • 展示使用朴素Dijkstra算法做法
import heapq
class Solution:def minTimeToReach(self, moveTime: List[List[int]]) -> int:# 首先先使用 堆优化的Dijkstra进行解题# 图已经构建,就是moveTime# dis[i][j]表示(0,0)到(i,j)的最短的时间n,m = len(moveTime),len(moveTime[0])dis = [[float('inf')]*m for _ in range(n)]dis[0][0] = 0done = [[False]*m for _ in range(n)]while True:x,y = -1,-1# 开始遍历还没确定的点for i in range(n):for j in range(m):if not done[i][j] and ((x<0 and y <0) or dis[i][j] < dis[x][y]):x,y = i,jif x<0 and y <0:# 说明都找到了return dis[n-1][m-1]# 设置已经找到done[x][y] = True# 访问邻居for i,j in (x+1,y),(x-1,y),(x,y+1),(x,y-1):if 0<= i < n and 0<= j < m:dis[i][j] = min(max(dis[x][y],moveTime[i][j]) + 1,dis[i][j])
  • 展示使用堆优化的Dijkstra算法
import heapq
class Solution:def minTimeToReach(self, moveTime: List[List[int]]) -> int:# 首先先使用 堆优化的Dijkstra进行解题# 图已经构建,就是moveTime# dis[i][j]表示(0,0)到(i,j)的最短的时间n,m = len(moveTime),len(moveTime[0])dis = [[float('inf')]*m for _ in range(n)]dis[0][0] = 0h = [(0,0,0)]while True:d,x,y = heapq.heappop(h)if x == n-1 and y == m-1:return d # 已经更新过了if d > dis[x][y]:continue# 访问邻居:for i,j in (x+1,y),(x-1,y),(x,y+1),(x,y-1):if 0<= i <n and 0<= j < m:# 合法的坐标# 计算当前的距离,小于才入堆new_dis = max(d,moveTime[i][j])+1if dis[i][j]>new_dis:dis[i][j] = new_disheapq.heappush(h,(dis[i][j],i,j))

相关文章:

图论 之 迪斯科特拉算法求解最短路径

文章目录 题目743.网络延迟时间3341.到达最后一个房间的最少时间I 求解最短路径的问题&#xff0c;分为使用BFS和使用迪斯科特拉算法&#xff0c;这两种算法求解的范围是有区别的 BFS适合求解&#xff0c;边的权值都是1的图中的最短路径的问题 图论 之 BFS迪斯科特拉算法适合求…...

掌握Spring开发_常用注解详解

1. 前言 1.1 写作目的 本文旨在全面解析Spring框架中常用的注解,帮助开发者更好地理解和使用这些注解,提高开发效率和代码质量。Spring框架提供了丰富的注解,简化了依赖注入、AOP、事务管理、Web开发等多个方面的开发工作。通过本文的学习,读者可以掌握这些注解的使用方法…...

华为昇腾服务器(固件版本查询、驱动版本查询、CANN版本查询)

文章目录 1. **查看固件和驱动版本**2. **查看CANN版本**3. **其他辅助方法**注意事项 在华为昇腾服务器上查看固件、驱动和CANN版本的常用方法如下&#xff1a; 1. 查看固件和驱动版本 通过命令行工具 npu-smi 执行以下命令查看当前设备的固件&#xff08;Firmware&#xff0…...

Kubernetes的Ingress和Service有什么区别?

在Kubernetes中&#xff0c;Ingress和Service是两个不同的概念&#xff0c;它们在功能、作用范围、应用场景等方面存在明显区别&#xff0c;具体如下&#xff1a; 功能 Ingress&#xff1a;主要用于管理集群外部到内部服务的HTTP和HTTPS流量路由。它可以根据域名、路径等规则…...

洛谷B3619(B3620)

B3619 10 进制转 x 进制 - 洛谷 B3620 x 进制转 10 进制 - 洛谷 代码区&#xff1a; #include<algorithm> #include<iostream> #include<vector> using namespace std;int main(){int n,x;cin >> n >> x;vector<char> arry;while(n){if(…...

vue组件,父子通信,路由,异步请求后台接口,跨域

1.组件注册 1.1局部注册 局部注册组件---1.导入import 组件对象名 from 组件网页路径 export default{ name:"名称", data(){return {}}, created(){}, …...

详解分布式ID实践

引言 分布式ID&#xff0c;所谓的分布式ID&#xff0c;就是针对整个系统而言&#xff0c;任何时刻获取一个ID&#xff0c;无论系统处于何种情况&#xff0c;该值不会与之前产生的值重复&#xff0c;之后获取分布式ID时&#xff0c;也不会再获取到与其相同的值&#xff0c;它是…...

.NET + Vue3 的前后端项目在IIS的发布

目录 一、发布准备 1、安装 IIS 2、安装 Windows Hosting Bundle&#xff08;.NET Core 托管捆绑包&#xff09; 3、安装 IIS URL Rewrite 二、项目发布 1、后端项目发布 2、前端项目发布 3、将项目部署到 IIS中 三、网站配置 1、IP配置 2、防火墙配置 3、跨域配置…...

软件测试之压力测试

&#x1f345; 点击文末小卡片&#xff0c;免费获取软件测试全套资料&#xff0c;资料在手&#xff0c;涨薪更快 压力测试 压力测试是一种软件测试&#xff0c;用于验证软件应用程序的稳定性和可靠性。压力测试的目标是在极其沉重的负载条件下测量软件的健壮性和错误处理能力&…...

矩阵-矩阵置零

矩阵置零 给定一个 m x n 的矩阵&#xff0c;如果一个元素为 0 &#xff0c;则将其所在行和列的所有元素都设为0 。请使用 原地 算法。在计算机科学中&#xff0c;一个原地算法&#xff08;in-place algorithm&#xff09;是一种使用小的&#xff0c;固定数量的额外之空间来转…...

【JavaScript】《JavaScript高级程序设计 (第4版) 》笔记-Chapter19-表单脚本

十九、表单脚本 表单脚本 JavaScript 较早的一个用途是承担一部分服务器端表单处理的责任。虽然 Web 和 JavaScript 都已经发展了很多年&#xff0c;但 Web 表单的变化不是很大。由于不能直接使用表单解决问题&#xff0c;因此开发者不得不使用JavaScript 既做表单验证&#xf…...

【C# 数据结构】队列 FIFO

目录 队列的概念FIFO (First-In, First-Out)Queue<T> 的工作原理&#xff1a;示例&#xff1a;解释&#xff1a; 小结&#xff1a; 环形队列1. **FIFO&#xff1f;**2. **环形缓冲队列如何实现FIFO&#xff1f;**关键概念&#xff1a; 3. **环形缓冲队列的工作过程**假设…...

论文笔记-WWWCompanion2024-LLM as Data Augmenters for Cold-Start Item Recommendation

论文笔记-WWW Companion 2024-Large Language Models as Data Augmenters for Cold-Start Item Recommendation 大语言模型作为冷启动项目推荐的数据增强器摘要1.引言2.前言3.LLMs作为数据增强3.1增强数据生成3.2成对比较损失 4.实验4.1实验设置4.2结果和分析4.3超参数实验 5.总…...

Java 语法新特性(Records、Pattern Matching、Sealed Classes)深度解析(11/17/21)✨

一、Records&#xff08;Java 16&#xff09; &#x1f4dd; 核心价值&#xff1a;简化不可变数据载体的定义 // 传统POJO vs Record public record User(String name, int age) {} // 自动生成&#xff1a;构造方法/equals()/hashCode()/toString() User user new User(&qu…...

QUdpSocket的readyRead信号只触发一次

问题 QUdpSocket的readyRead信号只触发一次。 原因 on_readyRead槽函数里必须读出现有数据后&#xff0c;才能触发新的事件。 解决办法 在on_readyRead槽函数里取出数据。 void MainWindow::on_readyRead() {qDebug() << "on_readyRead in";while (m_udp…...

jsherp importItemExcel接口存在SQL注入

一、漏洞简介 很多人说管伊佳ERP&#xff08;原名&#xff1a;华夏ERP&#xff0c;英文名&#xff1a;jshERP&#xff09;是目前人气领先的国产ERP系统虽然目前只有进销存财务生产的功能&#xff0c;但后面将会推出ERP的全部功能&#xff0c;有兴趣请帮点一下 二、漏洞影响 …...

测试data_management函数

测试data_management函数 这是我最近正在开发的AI工具信息平台的部门功能模块测试&#xff0c;基于streamlit架构。整理出来与大家分享&#xff0c;也为我以后自己回溯找到资源。 为了测试 data_management 函数并结合 Excel 文件中的 “Tools” 表单内容&#xff0c;我们需要…...

微信小程序---计划时钟设计与实现

微信小程序-计划时钟已上线,欢迎各位小伙伴的测试和使用~(微信小程序搜计划时钟即可使用) 在这篇博客中,我们将探讨如何在微信小程序中设计和实现一个任务管理功能,该功能允许用户添加、删除和查看任务。任务管理系统的核心是基于日期和时间的任务管理,可以设置任务的开…...

深度学习之图像回归(二)

前言 这篇文章主要是在图像回归&#xff08;一&#xff09;的基础上对该项目进行的优化。&#xff08;一&#xff09;主要是帮助迅速入门 理清一个深度学习项目的逻辑 这篇文章则主要注重在此基础上对于数据预处理和模型训练进行优化前者会通过涉及PCA主成分分析 特征选择 后…...

深入理解HttpSecurity的设计

一、HttpSecurity的应用 在前章节的介绍中我们讲解了基于配置文件的使用方式,也就是如下的使用。 也就是在配置文件中通过 security:http 等标签来定义了认证需要的相关信息,但是在SpringBoot项目中,我们慢慢脱离了xml配置文件的方式,在SpringSecurity中提供了HttpSecurity…...

[10-3]软件I2C读写MPU6050 江协科技学习笔记(16个知识点)

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16...

大语言模型(LLM)中的KV缓存压缩与动态稀疏注意力机制设计

随着大语言模型&#xff08;LLM&#xff09;参数规模的增长&#xff0c;推理阶段的内存占用和计算复杂度成为核心挑战。传统注意力机制的计算复杂度随序列长度呈二次方增长&#xff0c;而KV缓存的内存消耗可能高达数十GB&#xff08;例如Llama2-7B处理100K token时需50GB内存&a…...

【电力电子】基于STM32F103C8T6单片机双极性SPWM逆变(硬件篇)

本项目是基于 STM32F103C8T6 微控制器的 SPWM(正弦脉宽调制)电源模块,能够生成可调频率和幅值的正弦波交流电源输出。该项目适用于逆变器、UPS电源、变频器等应用场景。 供电电源 输入电压采集 上图为本设计的电源电路,图中 D1 为二极管, 其目的是防止正负极电源反接, …...

RabbitMQ入门4.1.0版本(基于java、SpringBoot操作)

RabbitMQ 一、RabbitMQ概述 RabbitMQ RabbitMQ最初由LShift和CohesiveFT于2007年开发&#xff0c;后来由Pivotal Software Inc.&#xff08;现为VMware子公司&#xff09;接管。RabbitMQ 是一个开源的消息代理和队列服务器&#xff0c;用 Erlang 语言编写。广泛应用于各种分布…...

计算机基础知识解析:从应用到架构的全面拆解

目录 前言 1、 计算机的应用领域&#xff1a;无处不在的数字助手 2、 计算机的进化史&#xff1a;从算盘到量子计算 3、计算机的分类&#xff1a;不止 “台式机和笔记本” 4、计算机的组件&#xff1a;硬件与软件的协同 4.1 硬件&#xff1a;五大核心部件 4.2 软件&#…...

破解路内监管盲区:免布线低位视频桩重塑停车管理新标准

城市路内停车管理常因行道树遮挡、高位设备盲区等问题&#xff0c;导致车牌识别率低、逃费率高&#xff0c;传统模式在复杂路段束手无策。免布线低位视频桩凭借超低视角部署与智能算法&#xff0c;正成为破局关键。该设备安装于车位侧方0.5-0.7米高度&#xff0c;直接规避树枝遮…...

【无标题】湖北理元理律师事务所:债务优化中的生活保障与法律平衡之道

文/法律实务观察组 在债务重组领域&#xff0c;专业机构的核心价值不仅在于减轻债务数字&#xff0c;更在于帮助债务人在履行义务的同时维持基本生活尊严。湖北理元理律师事务所的服务实践表明&#xff0c;合法债务优化需同步实现三重平衡&#xff1a; 法律刚性&#xff08;债…...

[USACO23FEB] Bakery S

题目描述 Bessie 开了一家面包店! 在她的面包店里&#xff0c;Bessie 有一个烤箱&#xff0c;可以在 t C t_C tC​ 的时间内生产一块饼干或在 t M t_M tM​ 单位时间内生产一块松糕。 ( 1 ≤ t C , t M ≤ 10 9 ) (1 \le t_C,t_M \le 10^9) (1≤tC​,tM​≤109)。由于空间…...

智警杯备赛--excel模块

数据透视与图表制作 创建步骤 创建 1.在Excel的插入或者数据标签页下找到数据透视表的按钮 2.将数据放进“请选择单元格区域“中&#xff0c;点击确定 这是最终结果&#xff0c;但是由于环境启不了&#xff0c;这里用的是自己的excel&#xff0c;真实的环境中的excel根据实训…...

学习 Hooks【Plan - June - Week 2】

一、React API React 提供了丰富的核心 API&#xff0c;用于创建组件、管理状态、处理副作用、优化性能等。本文档总结 React 常用的 API 方法和组件。 1. React 核心 API React.createElement(type, props, …children) 用于创建 React 元素&#xff0c;JSX 会被编译成该函数…...