最短路模型——AcWing 188. 武士风度的牛

news2024/11/19 14:36:11

最短路模型

定义

最短路模型是图论中的一个经典问题,旨在寻找从图中一个顶点到另一个顶点的路径,使得这条路径上的边(或边的权重)之和最小。这一模型在许多实际问题中有着广泛的应用,比如网络路由、地图导航、物流配送等场景。

在图论中,最短路问题通常形式化为在一个加权图 G=(V,E)G=(V,E) 中寻找两个顶点 uu 和 vv 之间的最短路径,其中 VV 是顶点集,EE 是边集,每条边 e \in Ee∈E 都有一个非负权重 w(e)w(e)。目标是找到一条从 uu 到 vv 的路径,使得路径上所有边的权重之和最小。

运用情况

  1. 网络路由:在互联网中,数据包需要通过最少的延迟或最低的成本从源节点传输到目的节点,这可以看作是一个最短路径问题。
  2. 地图导航:为司机或行人提供从起点到终点的最快或距离最短的路线。
  3. 物流与供应链管理:确定货物从仓库到客户或从供应商到工厂的最优运输路线,以减少运输成本和时间。
  4. 电路设计:在集成电路设计中,选择信号传递的最短路径以减少延迟和功耗。
  5. 社交网络分析:分析两个人之间关系链的最短路径,用于推荐系统或影响力传播分析。

注意事项

  1. 负权重边:如果图中存在负权重边,则不能直接使用某些算法如Dijkstra算法,而应考虑Bellman-Ford算法或Floyd-Warshall算法,因为它们能处理负权。
  2. 环路检测:在有负权重边的情况下,需要检查是否存在负权重环,因为这样的环路会导致无限减小路径长度,从而使问题无解。
  3. 稠密图与稀疏图:根据图的密度选择合适的算法。例如,Floyd-Warshall算法适用于稠密图,而Dijkstra或A*算法更适合稀疏图。
  4. 多源或多目标:当需要计算多个源点到单个目标或多个目标的最短路径时,可能需要对算法进行适当调整或多次调用。

解题思路

  1. 理解问题:首先明确问题是否为单源最短路径还是多源最短路径,图中是否存在负权重边。
  2. 选择算法:根据问题的具体情况选择合适的算法。常见的算法有Dijkstra算法(适用于无负权的单源最短路径)、Bellman-Ford算法(可处理负权重但无负权重环)、Floyd-Warshall算法(解决所有顶点对之间的最短路径,适合稠密图)。
  3. 实现与优化:实现所选算法,并考虑如何优化,比如使用优先队列优化Dijkstra算法,或在特定情况下利用预处理技巧减少计算量。
  4. 验证结果:检查计算出的路径是否确实是最短的,并确保没有违反任何先决条件,如负权重环的存在。

AcWing 188. 武士风度的牛

题目描述

AcWing 188. 武士风度的牛 - AcWing

运行代码

#include <cstring>
#include <iostream>
#include <algorithm>
#define x first
#define y second
using namespace std;
typedef pair<int, int> PII;
const int N = 155, M = N * N;

int n, m;
char g[N][N];
PII q[M];
int dist[N][N];

int bfs()
{
    int dx[] = {-2, -1, 1, 2, 2, 1, -1, -2};
    int dy[] = {1, 2, 2, 1, -1, -2, -2, -1};
    int sx, sy;
    for (int i = 0; i < n; i ++ )
        for (int j = 0; j < m; j ++ )
            if (g[i][j] == 'K')
                sx = i, sy = j;

    int hh = 0, tt = 0;
    q[0] = {sx, sy};

    memset(dist, -1, sizeof dist);
    dist[sx][sy] = 0;

    while (hh <= tt)
    {
        PII t = q[hh ++ ];

        for (int i = 0; i < 8; i ++ )
        {
            int a = t.x + dx[i], b = t.y + dy[i];
            if (a < 0 || a >= n || b < 0 || b >= m) continue;
            if (g[a][b] == '*') continue;
            if (dist[a][b] != -1) continue;
            if (g[a][b] == 'H') return dist[t.x][t.y] + 1;

            dist[a][b] = dist[t.x][t.y] + 1;
            q[ ++ tt] = {a, b};
        }
    }

    return -1;
}

int main()
{
    cin >> m >> n;
    for (int i = 0; i < n; i ++ ) cin >> g[i];

    cout << bfs() << endl;

    return 0;
}

代码思路

  1. 包含文件和宏定义:

    • 包含了 <cstring><iostream> 和 <algorithm> 头文件,分别用于字符串处理、输入输出和算法操作。
    • 定义了一个宏 N 作为最大地图大小,并定义了类型别名 PII 为 pair<int, int>,用于存储坐标。
    • 使用 #define x first 和 #define y second 来简化 pair 对象的访问。
  2. 变量声明和初始化:

    • 声明了 n 和 m 分别代表地图的行数和列数,二维字符数组 g 存储地图信息,q 作为队列存储待访问的坐标,dist 数组记录每个位置到起点的最短距离。
    • 通过 memset 函数将 dist 数组初始化为 -1,表示未访问过。
  3. 核心函数 bfs():

    • 首先,通过双层循环遍历地图,找到起始位置 'K' 的坐标 (sx, sy)
    • 初始化队列 q,并将起始位置入队。
    • 进行广度优先搜索,定义了变量 hh 和 tt 作为队列的头尾指针,并用数组 dx 和 dy 来表示马可能的八个移动方向。
    • 在 BFS 循环中,每次从队列头部取出一个坐标,遍历其八个可能的下一个位置,检查这些位置是否越界、是否有障碍物('*')或是否已经访问过。若新位置有效且未访问,则更新该位置的最短距离,并将其加入队列。
    • 如果在搜索过程中遇到草('H'),立即返回当前的最短距离加一(因为起始点的初始距离为0)。
    • 若循环结束仍未找到草,则返回 -1 表示无解(根据题目描述,这种情况实际上不会发生)。
  4. 主函数 main():读取地图的列数 m 和行数 n,然后逐行读取地图信息。调用 bfs() 函数计算并输出最短跳跃次数。

改进思路

  1. 代码注释:添加详细的注释,特别是对于关键变量、数组含义、函数功能等进行说明,提高代码的可读性和维护性。

  2. 命名规范:变量命名可以更加直观,例如将 sx, sy 改为 startX, startY,将 hh, tt 改为 head, tail,以增加代码的自解释性。

  3. 宏定义优化:考虑到使用 #define x first 和 #define y second 可能导致的命名冲突和阅读困难,可以考虑直接在代码中使用 first 和 second,或者在BFS函数内部临时定义辅助函数来访问pair的元素。

  4. 避免全局变量:尽量减少全局变量的使用,可以将 nmgqdist 等变量作为 bfs 函数的参数传入,以减少不同部分间的耦合度。

  5. 边界检查和错误处理:虽然题目保证有解,但在实际应用中,增加对输入数据的校验(如检查地图尺寸是否合理,起点和终点是否存在等)可以提高程序的健壮性。

  6. 内存使用优化:当地图规模非常大时,可以考虑使用压缩存储或动态分配内存来减少空间消耗,例如只对访问过的节点分配dist数组的空间。

  7. 代码结构清晰化:将BFS逻辑拆分成几个小函数,如初始化队列、拓展节点等,可以让代码逻辑更清晰,便于阅读和维护。

  8. 使用标准库函数或STL容器:考虑使用std::queue代替原始数组实现队列,这样可以利用STL容器的便利性,减少手动管理数组指针的复杂度。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1882078.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

音频转文字怎么转?4个音频转文字的方法一定要知道

随着夏日脚步的到来&#xff0c;各类活动和准备工作也随之增多。 在这样一个忙碌的时期&#xff0c;整理会议的音频记录变得尤为关键。然而&#xff0c;单单依靠手动整理&#xff0c;不仅耗时耗力&#xff0c;还可能出现错漏。 但也不用太着急&#xff0c;下面将为大家介绍几…

生产者发送数据,kafka服务器接收数据异常的问题记录

现象&#xff1a; 某个客户要求审计日志用kafka的方式传输给他们&#xff0c;使用了第三方的librdkafka库来开发。 往客户提供的kafka服务器上的一个topic发送数据&#xff0c;这个topic有三个分区&#xff0c;客户反馈接收到的数据和发送端发送的实际数量对不上&#xff0c;他…

韩顺平0基础学java——第34天

p675-689 UDP网络编程 1.类 DatagramSocket和 DatagramPacket[数据包/数据报]实现了基于UDP协议网络程序。 2.UDP数据报通过数据报套接字DatagramSocket发送和接收&#xff0c;系统不保证UDP数据报一定能够安全送到目的地,也不能确定什么时候可以抵达。 3.DatagramPacket对象…

python-docx 设置水印字体

本文目录 前言一、水印的XML在哪里1、Word内置水印设置2、自定义XML部件3、Header or Footer二、确认位置三、水印表前解释1、水印XML源代码2、水印结构解析3、关于style的详解三、修改水印样式前言 本文我们来完成一个有趣的玩意儿:在Python中通过操作Word文档的XML来设置整…

MeterSphere v3.0全新启航,让软件测试工作更简单、更高效

2024年7月1日&#xff0c;MeterSphere v3.0版本正式发布。MeterSphere v3.0是新一代的测试管理和接口测试工具&#xff0c;致力于让软件测试工作更简单、更高效&#xff0c;不再成为持续交付的瓶颈。 在团队协作方面&#xff0c;针对目前企业软件测试团队所面临的测试工具不统…

【SpringBoot3学习 | 第2篇】SpringBoot3整合+SpringBoot3项目打包运行

文章目录 一. SpringBoot3 整合 SpringMVC1.1 配置静态资源位置1.2 自定义拦截器&#xff08;SpringMVC配置&#xff09; 二. SpringBoot3 整合 Druid 数据源三. SpringBoot3 整合 Mybatis3.1 Mybatis整合3.2 声明式事务整合配置3.3 AOP整合配置 四. SpringBoot3 项目打包和运行…

ROS学习笔记(17):建图与定位(1)

目录 0.前言 1.定位和建图 1.里程计&#xff08;Odometry&#xff09; 2.扫描匹配&#xff08;Scan Matching&#xff09; 3.结尾 0.前言 好久不见各位&#xff0c;前段时间忙着考试&#xff08;6级和一些专业课&#xff09;和摆烂断更了近30天&#xff0c;现在哥们回来更…

LaMa Image Inpainting 图像修复 OnnxRuntime-GPU版 Demo

目录 介绍 效果 模型信息 项目 代码 下载 LaMa Image Inpainting 图像修复 OnnxRuntime-GPU版 Demo 介绍 gihub地址&#xff1a;GitHub - advimman/lama: &#x1f999; LaMa Image Inpainting, Resolution-robust Large Mask Inpainting with Fourier Convolutions, …

昇思25天学习打卡营第八天|保存与加载

背景 提供免费算力支持&#xff0c;有交流群有值班教师答疑的华为昇思训练营进入第八天了。 今天是第八天&#xff0c;前七天的学习内容可以看链接 昇思25天学习打卡营第一天|快速入门 昇思25天学习打卡营第二天|张量 Tensor 昇思25天学习打卡营第三天|数据集Dataset 昇思25天…

Python对象不可哈希?教你几招解决!

目录 1、什么是可哈希?🚀 1.1 哈希基础理论 1.2 可哈希对象定义🔍 示例代码: 1.3 Python中哈希的作用 1.4 哈希表与性能提升📈 应用实例代码: 2、Python中的哈希特性🔑 2.1 不变性与哈希值🔄 示例代码展示: 2.2 实现细节深入探讨📚 深入代码细节:…

深度学习论文: VanillaNet: the Power of Minimalism in Deep Learning

深度学习论文: VanillaNet: the Power of Minimalism in Deep Learning VanillaNet: the Power of Minimalism in Deep Learning PDF:https://arxiv.org/pdf/2305.12972 PyTorch: https://github.com/shanglianlm0525/PyTorch-Networks 1 概述 提出的VanillaNet通过简化设计&…

【机器学习】Python sorted 函数

目录&#xff1a; 什么是sorted()函数列表降序排序应用到字符串自定义排序规则实际应用 Python中的内置函数——sorted()。 1. 什么是sorted()函数 在Python中&#xff0c;sorted()是一个内置函数&#xff0c;用于对任何可迭代对象&#xff08;如列表、元组、字符串等&…

绿联NAS进入SSH的方法

1. 进入【设备管理】&#xff0c;在调试功能中&#xff0c;开启远程调试功能&#xff0c;发送手机验证码&#xff0c;你将得到一个3天有效期的验证码&#xff0c;就是ssh登录密码。 2. 使用终端工具或ssh命令直接登录SSH。 端口是922&#xff0c;账号是&#xff1a;root&#…

七月论文审稿GPT第5版:拿我司七月的早期paper-7方面review数据集微调LLama 3

前言 llama 3出来后&#xff0c;为了通过paper-review的数据集微调3&#xff0c;有以下各种方式 不用任何框架 工具 技术&#xff0c;直接微调原生的llama 3&#xff0c;毕竟也有8k长度了 效果不期望有多高&#xff0c;纯作为baseline通过PI&#xff0c;把llama 3的8K长度扩展…

李沐深度学习知识点—数值稳定性、模型激活函数、全连接层到卷积、卷积层

数值稳定性 其中h是一个向量&#xff0c;向量关于向量的倒数是一个矩阵&#xff0c;因此求梯度是求矩阵乘法 矩阵乘法带来了 梯度爆炸&#xff0c;梯度消失 模型初始化和激活函数 归一化&#xff1a;不管梯度多大&#xff0c;我都把梯度拉回来&#xff0c;否的出现梯度爆炸和梯…

【基础篇】第4章 Elasticsearch 查询与过滤

在Elasticsearch的世界里&#xff0c;高效地从海量数据中检索出所需信息是其核心价值所在。本章将深入解析查询与过滤的机制&#xff0c;从基础查询到复合查询&#xff0c;再到全文搜索与分析器的定制&#xff0c;为你揭开数据检索的神秘面纱。 4.1 基本查询 4.1.1 Match查询…

内容个性化的智能引擎:Kompas.ai如何满足用户需求

在数字化时代&#xff0c;用户对内容的消费趋向个性化和定制化。个性化内容不仅能提升用户体验&#xff0c;还能增强品牌与用户之间的互动。Kompas.ai作为一款先进的智能引擎&#xff0c;正通过其独特的技术满足用户的个性化需求。 个性化内容的重要性 个性化内容在提升用户体验…

2024 vue3入门教程:01vscode终端命令创建第一个vue项目

参考vue官网手册&#xff1a;https://cn.vuejs.org/guide/quick-start.html 一、找个盘符&#xff0c;新建文件夹存储以后得vue项目 我的是e盘下创建了vueproject 二、使用vscode打开存储vue项目的文件夹 因为我生成过项目&#xff0c;所以有文件&#xff0c;你们初次是没有…

分布式存储和分布式计算两个哪个更适合作为工作深入方向发展?

有朋友问&#xff0c;分布式存储比如hdfs&#xff0c;ceph&#xff0c;minio&#xff0c;tidb&#xff0c;glusterfs&#xff1b;分布式计算比如Hadoop&#xff0c;spark&#xff0c;flink&#xff1b;它们在实际工作中咋样&#xff1f;具体开发工作是啥&#xff1f;哪个更有发…

leetCode.96. 不同的二叉搜索树

leetCode.96. 不同的二叉搜索树 题目思路 代码 // 方法一&#xff1a;直接用卡特兰数就行 // 方法二&#xff1a;递归方法 class Solution { public:int numTrees(int n) {// 这里把 i当成整个结点&#xff0c;j当成左子树最左侧结点,并一次当根节点尝试// f[ i ] f[ j - 1…