代码随想录算法训练营第59天|卡码网 47. 参加科学大会、94. 城市间货物运输 I

news2024/9/28 20:16:51

1. 卡码网 47. 参加科学大会

题目链接:https://kamacoder.com/problempage.php?pid=1047
文章链接:https://www.programmercarl.com/kamacoder/0047.参会dijkstra堆.html#总结
在这里插入图片描述

思路依然是 dijkstra 三部曲:
1.第一步,选源点到哪个节点近且该节点未被访问过
2.第二步,该最近节点被标记访问过
3.第三步,更新非访问节点到源点的距离(即更新minDist数组)
只不过之前是 通过遍历节点来遍历边,通过两层for循环来寻找距离源点最近节点。 这次我们直接遍历边,且通过堆来对边进行排序,达到直接选择距离源点最近节点。
优化部分
1.针对稀疏图,从边的角度使用邻接表进行图存储。
2.选源点到哪个节点近且该节点未被访问过。
我们要选择距离源点近的节点(即:该边的权值最小),所以 我们需要一个 小顶堆 来帮我们对边的权值排序,每次从小顶堆堆顶 取边就是权值最小的边。注意:这里的权值是节点到源点的权值,小顶堆需要按照该权值来排序。
小顶堆可以使用优先级队列实现。最小堆中保存着所有未被访问的且权值不是默认最大值的节点。
3.该最近节点被标记访问过
和 朴素dijkstra 一样。
4.更新非访问节点到源点的距离(即更新minDist数组)
和 朴素dijkstra 一样。唯一的区别是因为使用的是邻接表,则可以直接获取到当前最近节点的所有直连节点,而不用同邻接矩阵一样,需要遍历所有节点再判断。

class Edge {
    int to; // 邻接顶点
    int val; // 边的权值
    Edge(int to,int val) {
        this.to = to;
        this.val = val;
    }
}

class MyComparison implements Comparator<Pair<Integer,Integer>> {
    @Override
    public int compare(Pair<Integer,Integer> a,Pair<Integer,Integer> b) {
        return Integer.compare(a.second,b.second); // 权值排序
    }
}

class Pair<U,V> {
    public final U first; // 节点
    public final V second; // 节点到源点的最小权值
    public Pair(U first,V second) {
        this.first = first;
        this.second = second;
    }
}

public class Main {
    public static void main(String[] args) {
        Scanner scanner = new Scanner(System.in);
        int n = scanner.nextInt(); // 公共汽车站数量
        int m = scanner.nextInt(); // 公路数量
        
        List<List<Edge>> grid = new ArrayList<>(n+1);
        for (int i=0;i<=n;i++) {
            grid.add(new ArrayList<>());
        }
        
        for (int i=0;i<m;i++) {
            int p1 = scanner.nextInt();
            int p2 = scanner.nextInt();
            int val = scanner.nextInt();
            grid.get(p1).add(new Edge(p2,val));
        }
        
        int start = 1; // 起点
        int end = n; // 终点
        
        // 存储从源点到每个节点的最短距离
        int[] minDist = new int[n+1];
        Arrays.fill(minDist,Integer.MAX_VALUE);
        
           // 记录顶点是否被访问过
        boolean[] visited = new boolean[n + 1];
        
        // 优先队列中存放Pair<节点,源点到该节点的权值>
        PriorityQueue<Pair<Integer, Integer>> pd = new PriorityQueue<>(new MyComparison());
        
        // 初始化队列,源点到源点的距离为0,所以初始为0
        pd.add(new Pair<>(start,0));
        
        minDist[start] = 0; // 起始点到自身的距离为0
        
        while (!pd.isEmpty()) {
            // 1. 第一步 选源点到哪个节点近且该节点未被访问过
            Pair<Integer,Integer> cur = pd.poll();
            if (visited[cur.first]) continue; // 注意:因为最小堆中会存在多个不同权值的相同节点。当该节点的最小权值节点被取出后,
            //节点会被标记为被访问true。那么该节点的其他权值节点就无用了,直接跳过。
            
            // 2. 第二步,该最近节点被标记访问过
            visited[cur.first] = true;
            
            // 3. 第三步,更新非访问节点到源点的距离
            for (Edge edge:grid.get(cur.first)) {
                if (!visited[edge.to] && minDist[cur.first] + edge.val < minDist[edge.to]) {
                    minDist[edge.to] = minDist[cur.first] + edge.val;
                    pd.add(new Pair<>(edge.to,minDist[edge.to])); // 将更新后的距源点的权值的节点加入到最小堆中
                    // 注意:这里并没有删除原来权值的相同节点,而是将新的最小权值作为新的节点加入了最小堆中。
                    // 也就是说最小堆中会存在多个不同权值的相同节点。
                    
                }
            }
         }
         
         if (minDist[end] == Integer.MAX_VALUE) {
             System.out.println(-1);
         } else {
             System.out.println(minDist[end]);
         }
         
        
    }
}

2. 卡码网 94. 城市间货物运输 I

题目链接:https://kamacoder.com/problempage.php?pid=1152
文章链接:https://www.programmercarl.com/kamacoder/0094.城市间货物运输I.html

在这里插入图片描述

思路:
使用Bellman_ford算法
核心思想是 对所有边进行松弛n-1次操作(n为节点数量),从而求得目标最短路。
针对:图中边的权值可以有负数,且不存在任何负权回路的情况(在有向图中出现有向环 且环的总权值为负数)。
对所有边松弛一次,可以计算 起点到达 与起点一条边相连的节点 的最短距离。
对所有边松弛两次,可以计算 起点到达 与起点两条边相连的节点 的最短距离。
对所有边松弛三次,可以计算 起点到达 与起点三条边相连的节点 的最短距离。
若计算起点到终点的最短距离,则需要对边松弛n-1次,其中n为节点数。

import java.util.*;

public class Main {
    public static void main (String[] args) {
        Scanner sc = new Scanner(System.in);
        int n = sc.nextInt(); // 城市数量
        int m = sc.nextInt(); // 道路数量
        
        List<List<Integer>> roadList = new ArrayList<>();
        for (int i=0;i<m;i++) {
            int s = sc.nextInt();
            int t = sc.nextInt();
            int v = sc.nextInt();
            List<Integer> list = new ArrayList<>();
            list.add(s);
            list.add(t);
            list.add(v);
            roadList.add(list);
        }
        
        int[] minDist = new int[n+1]; // 记录起点到各个节点的最短距离
        Arrays.fill(minDist,Integer.MAX_VALUE);
        minDist[1]=0;
        
        // 松弛n-1次
        for(int j=1;j<n;j++) {
            // 对所有道路进行分析
            for(int i=0;i<m;i++) {
                int from = roadList.get(i).get(0);
                int to = roadList.get(i).get(1);
                int value = roadList.get(i).get(2);
                if (minDist[from] != Integer.MAX_VALUE && minDist[from] + value < minDist[to]) {
                    minDist[to] = minDist[from] + value;
                }
            }
        }
        
        if (minDist[n] == Integer.MAX_VALUE) {
            System.out.println("unconnected");
        } else {
            System.out.println(minDist[n]);
        }
        
    }
}

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

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

相关文章

Hadoop HDFS命令操作实例

一.创建与查看HDFS目录 每次重启后&#xff0c;Jps和java -version执行出来的结果不符合就使用 source ~/.bash_profile 是在 Unix/Linux 系统上用来重新加载用户的 Bash 配置文件 ~/.bash_profile 的命令。这条命令的作用是使得当前的 Bash 环境重新读取并应用 ~/.bash_pro…

Android studio安装问题及解决方案

Android studio安装问题及解决方案 gradle已经安装好了&#xff0c;但是每次就是找不到gradle的位置&#xff0c;每次要重新下载&#xff0c;很慢&#xff0c;每次都不成功 我尝试用安装android studio时自带的卸载程序&#xff0c;卸载android studio&#xff0c;然后重新下…

Centos8.5.2111(2)之基于docker容器的SELinux及防火墙配置与管理

对于Linux服务器而言&#xff0c;常用netfilter/iptables数据包过滤系统。Centos 8采用了firewalld取代了iptables。firewalld和iptables其实都不是真正的防火墙&#xff0c;只是定义策略的防火墙工具而已。 SELinux全称为“Security-Enhanced Linux”&#xff0c;是安全增强型…

移情别恋c++ ദ്ദി˶ー̀֊ー́ ) ——15.红黑树

1.红黑树的概念 红黑树&#xff0c;是一种二叉搜索树&#xff0c;但在每个结点上增加一个存储位表示结点的颜色&#xff0c;可以是Red或 Black。 通过对任何一条从根到叶子的路径上各个结点着色方式的限制&#xff0c;红黑树确保没有一条路 径会比其他路径长出俩倍&#xff0c;…

产品包装检测系统源码分享

货架产品包装检测检测系统源码分享 [一条龙教学YOLOV8标注好的数据集一键训练_70全套改进创新点发刊_Web前端展示] 1.研究背景与意义 项目参考AAAI Association for the Advancement of Artificial Intelligence 项目来源AACV Association for the Advancement of Computer…

Java文件I/O处理之RandomAccessFile【随意存取文件】

Java语言有一个处理文件输入输出的RandomAccessFile类&#xff0c;既可以读取文件内容&#xff0c;也可以向文件输出数据。 RandomAccessFile类在国内的技术文档和书籍中都翻译为“随机访问文件”类&#xff0c;确实令人不解。 在中文中“随机”的意思&#xff1a; 不设任何条…

流量新密码?AI宠物定制写真在小红书爆火,有人搞了10W+

大家好&#xff0c;我是灵魂画师向阳 不知道大家发现没&#xff1f;消费者对于情感价值的需求猛增&#xff0c;宠物服务行业衍生出越来越多的“拟人化”新业态。 宠物摄影和写真成为宠物经济中的新兴行业&#xff0c;吸引了越来越多的摄影师和养宠人的关注。 一些摄影师和摄…

《开题报告》基于SSM框架的电影评论网站的设计与实现源码++学习文档+答辩讲解视频

开题报告 研究背景 随着互联网技术的飞速发展&#xff0c;网络已成为人们获取信息、交流思想、分享体验的重要平台。在电影产业蓬勃发展的今天&#xff0c;观众对于电影的选择不再仅仅依赖于传统的宣传渠道&#xff0c;而是更加倾向于通过在线平台了解影片内容、观看预告片、…

C++基础知识十

1.string尾插 在一个string类型的字符后面插入其它的字符可以用push_back和append&#xff0c;这俩个是常用的。 #include<iostream> using namespace std; int main() {string s1("hello");s1.push_back( );s1.push_back(w);s1.push_back(o);s1.push_back(r…

实施自动化测试的五个条件

摘要&#xff1a; 谈到什么是组成一次自动化测试的“恰当实施”经常会关注你需要用的工具&#xff0c;但是那仅仅是等式的一部分。巴斯 迪杰斯特拉详细说明了你需要考虑的其他四件事&#xff0c;他们如何致力于你的自动化测试的成功&#xff0c;以及关联到不能适当关注它们中任…

如何存储你需要的信息:变量——WEB开发系列42

变量是一种用于存储数据的基本工具。它允许我们在代码中给某个数据赋予一个名字&#xff0c;便于在后续的代码中引用、更新、甚至重新赋值。 一、什么是变量&#xff1f; 变量本质上是一个“容器”&#xff0c;它存储特定的信息或数据。你可以把变量想象成一个标签&#xff0c…

巧用switch-case消除条件判断

shigen坚持更新文章的博客写手&#xff0c;记录成长&#xff0c;分享认知&#xff0c;留住感动。个人IP&#xff1a;shigen 在之前的文章中&#xff0c;我们有提交消除if-else代码的方法&#xff1a; 结合HashMap与Java 8的Function和Optional消除ifelse判断巧用枚举消除逻辑判…

工控主板在工业控制中扮演什么角色

工控主板在工业控制中扮演着至关重要的角色&#xff0c;它是工业控制系统的核心组件&#xff0c;负责连接、控制和管理各种工业设备&#xff0c;实现自动化生产和智能化管理。具体来说&#xff0c;工控主板在工业控制中的作用可以归纳为以下几个方面&#xff1a; 一、核心控制…

MNIST手写数字数据集

数据集 官网链接失效&#xff0c;我找到数据集后&#xff0c;上传到码云&#xff0c;并在这里分享。 打开链接&#xff0c;进入如下目录&#xff0c;即可找到如下八个文件&#xff1a; 下面是一些可有可无的介绍。 Mnist数据集介绍 Mnist数据集包含70000张手写数字图片&#x…

IO(Reader/Writer)

1.Reader a.简介 i.是Java的IO库提供的另一种输入流。和InputStream的区别是&#xff1a;InputStream是字节流&#xff0c;以byte为单位&#xff0c;Reader是字符流&#xff0c;以char为单位。 ii.java.io.Reader是所有字符输入流的超类。 b.FileReader i.FileReader默认的编…

【Kubernetes】常见面试题汇总(四十三)

目录 98. kube-apiserver 和 kube-scheduler 的作用是什么&#xff1f; 99.您对云控制器管理器了解多少&#xff1f; 特别说明&#xff1a; 题目 1-68 属于【Kubernetes】的常规概念题&#xff0c;即 “ 汇总&#xff08;一&#xff09;~&#xff08;二十二&#xff09;…

甘肃辣椒油:舌尖上的热辣诱惑

&#x1f4a5;宝子们&#xff0c;今天必须要给你们安利甘肃食家巷的辣椒油&#x1f336;️&#xff01;✨甘肃辣椒油&#xff0c;那可是有着独特魅力的美食瑰宝&#x1f60d;。它以其鲜艳的色泽、浓郁的香气和醇厚的辣味&#xff0c;瞬间点燃你的味蕾&#x1f525;。&#x1f3…

关于聚类算法的一份介绍

在这篇文章中我将介绍无监督算法中“聚类”部分的知识&#xff0c;其中关于K均值聚类、层次聚类、密度聚类部分我将各附上一份实际运用的代码&#xff0c;而其余的像学习向量量化、高斯混合聚类部分则只是简单介绍下概念。 一、 关于聚类 首先我先简单介绍下聚类算法有关的东…

2024年7月大众点评温州美食店铺基础信息

在做一些城市分析、学术研究分析、商业选址、商业布局分析等数据分析挖掘时&#xff0c;大众点评的数据参考价值非常大&#xff0c;截至2024年7月&#xff0c;大众点评美食店铺剔除了暂停营业、停止营业后的最新数据情况分析如下。 温州餐饮美食店铺约6.5万家&#xff0c;有均…

CTF-SSH私钥泄露

CTF-SSH私钥泄露 一.信息探测--查看开放的服务--分析探测结果-- 探测大端口的信息 深入挖掘ssh信息![在这里插入图片描述](https://i-blog.csdnimg.cn/blog_migrate/6baf0b5de72d537c7093d3e2394d93cd.png#pic_center)解密ssh秘钥信息 工具&#xff1a;kali Linux 一.信息探测…