【LeetCode每日一题合集】2023.9.11-2023.9.17(⭐反悔贪心拓扑排序Floyd)

news2025/1/18 8:50:48

文章目录

  • 630. 课程表 III
    • 解法——反悔贪心⭐⭐⭐⭐⭐
  • 1462. 课程表 IV⭐
    • 解法1——拓扑排序预处理
    • 解法2——Floyd算法判断是否存在路径
  • 2596. 检查骑士巡视方案(方向模拟)
  • 1222. 可以攻击国王的皇后(方向模拟)
  • LCP 50. 宝石补给(简单模拟)
  • 198. 打家劫舍(经典线性DP)
  • 213. 打家劫舍 II(循环打家劫舍)
    • 代码写法1——另写方法robR(l, r)
    • 代码写法2——二维dp数组

630. 课程表 III

https://leetcode.cn/problems/course-schedule-iii/description/?envType=daily-question&envId=2023-09-11
在这里插入图片描述

提示:
1 <= courses.length <= 10^4
1 <= durationi, lastDayi <= 10^4

解法——反悔贪心⭐⭐⭐⭐⭐

https://leetcode.cn/problems/course-schedule-iii/solutions/2436667/tan-xin-huan-neng-fan-hui-pythonjavacgoj-lcwp/?envType=daily-question&envId=2023-09-11

class Solution {
    public int scheduleCourse(int[][] courses) {
        // 按照截止时间从小到大排序
        Arrays.sort(courses, (a, b) -> a[1] - b[1]);
        // 最大堆
        PriorityQueue<Integer> pq = new PriorityQueue<>((a, b) -> b - a);
        int day = 0;        // 记录当前使用了多少天
        for (int[] c: courses) {
            int d = c[0], t = c[1];
            if (day + d <= t) {
                // 如果可以学,直接学
                day += d;
                pq.offer(d);
            } else if (!pq.isEmpty() && pq.peek() > d) {
                // 如果不可以学,检查已经选了的课程中有没有耗时更长的替换掉
                day -= pq.poll() - d;
                pq.offer(d);
            }
        }
        // 最后的答案就是队列中已选课程的数量
        return pq.size();
    }
}

更多反悔贪心可见:
【算法】反悔贪心
【力扣周赛】第 357 场周赛(⭐反悔贪心)

1462. 课程表 IV⭐

https://leetcode.cn/problems/course-schedule-iv/?envType=daily-question&envId=2023-09-12
在这里插入图片描述

提示:

2 <= numCourses <= 100
0 <= prerequisites.length <= (numCourses * (numCourses - 1) / 2)
prerequisites[i].length == 2
0 <= ai, bi <= n - 1
ai != bi
每一对 [ai, bi] 都 不同
先修课程图中没有环。
1 <= queries.length <= 10^4
0 <= ui, vi <= n - 1
ui != vi

解法1——拓扑排序预处理

关于拓扑排序可见:【算法基础:搜索与图论】3.3 拓扑排序
在拓扑排序过程中多加一层循环,用来处理各个节点之间是否为先决条件。 回复查询时只需要 O ( 1 ) O(1) O(1)查询。

class Solution {
    public List<Boolean> checkIfPrerequisite(int numCourses, int[][] prerequisites, int[][] queries) {
        List<Boolean> ans = new ArrayList<>();
        List<Integer>[] g = new ArrayList[numCourses];
        int[] in = new int[numCourses];
        Arrays.setAll(g, e -> new ArrayList<Integer>());
        boolean[][] isPre = new boolean[numCourses][numCourses];
        for (int[] p: prerequisites) {
            g[p[0]].add(p[1]);
            in[p[1]]++;
            isPre[p[0]][p[1]] = true;
        }
        // 拓扑排序预处理出n^2各个节点是否是其它节点的先决条件
        Queue<Integer> q = new LinkedList<>();
        for (int i = 0; i < numCourses; ++i) {
            if (in[i] == 0) q.offer(i);
        }
        while (!q.isEmpty()) {
            int x = q.poll();
            for (int y: g[x]) {
                for (int i = 0; i < numCourses; ++i) {
                    isPre[i][y] |= isPre[i][x];
                }
                if (--in[y] == 0) q.offer(y);
            }
        }
        // O(1) 回答查询
        for (int[] query: queries) {
            ans.add(isPre[query[0]][query[1]]);
        }
        return ans;
    }
}

解法2——Floyd算法判断是否存在路径

关于Floyd算法可见:【算法基础:搜索与图论】3.4 求最短路算法(Dijkstra&bellman-ford&spfa&Floyd)

class Solution {
    public List<Boolean> checkIfPrerequisite(int numCourses, int[][] prerequisites, int[][] queries) {
        boolean[][] g = new boolean[numCourses][numCourses];
        for (int[] p: prerequisites) {
            g[p[0]][p[1]] = true;
        }
        // Floyd三重循环
        for (int k = 0; k < numCourses; ++k) {
            for (int i = 0; i < numCourses; ++i) {
                for (int j = 0; j < numCourses; ++j) {
                    g[i][j] = g[i][j] | (g[i][k] & g[k][j]);
                }
            }
        }
        // 回复查询
        List<Boolean> ans = new ArrayList<>();
        for (int[] q: queries) {
            ans.add(g[q[0]][q[1]]);
        }
        return ans;
    }
}

2596. 检查骑士巡视方案(方向模拟)

https://leetcode.cn/problems/check-knight-tour-configuration/?envType=daily-question&envId=2023-09-13

在这里插入图片描述
提示:
n == grid.length == grid[i].length
3 <= n <= 7
0 <= grid[row][col] < n * n
grid 中的所有整数 互不相同

按题意模拟八个方向即可。

class Solution {
    int[] dx = {-1, -2, -2, -1, 1, 2, 2, 1}, dy = new int[]{-2, -1, 1, 2, 2, 1, -1, -2};

    public boolean checkValidGrid(int[][] grid) {
        int n = grid.length;
        int x = 0, y = 0;
        for (int i = 0; i < n * n - 1; ++i) {   // 检查每一步
            boolean f = false;
            for (int k = 0; k < 8; ++k) {       // 尝试8个方向
                int nx = x + dx[k], ny = y + dy[k];
                if (nx >= 0 && ny >= 0 && nx < n && ny < n && grid[nx][ny] == grid[x][y] + 1) {
                    x = nx;
                    y = ny;
                    f = true;
                    break;
                }
            }
            if (!f) return false;
        }
        return true;
    }
}

1222. 可以攻击国王的皇后(方向模拟)

https://leetcode.cn/problems/queens-that-can-attack-the-king/description/

在这里插入图片描述
在这里插入图片描述
提示:

1 <= queens.length <= 63
queens[i].length == 2
0 <= queens[i][j] < 8
king.length == 2
0 <= king[0], king[1] < 8
一个棋盘格上最多只能放置一枚棋子。

将所有皇后放入一个哈希集合中。

从国王位置开始,枚举8个方向,走8步,如果遇到的位置存在于皇后集合中,则将其加入答案。

class Solution {
    public List<List<Integer>> queensAttacktheKing(int[][] queens, int[] king) {
        List<List<Integer>> ans = new ArrayList<>();
        Set<Integer> s = new HashSet<>();
        for (int[] q: queens) s.add(q[0] * 10 + q[1]);
        int[] dx = {-1, -1, 0, 1, 1, 1, 0, -1}, dy = {0, 1, 1, 1, 0, -1, -1, -1};
        int x = king[0], y = king[1];
        for (int i = 0; i < 8; ++i) {           // 枚举8个方向
            for (int k = 1; k < 8; ++k) {       // 枚举8步
                int nx = x + dx[i] * k, ny = y + dy[i] * k;
                if (nx >= 0 && ny >= 0 && nx < 8 && ny < 8) {
                    if (s.contains(nx * 10 + ny)) {
                        ans.add(List.of(nx, ny));
                        break;
                    }
                } else break;
            }
        }
        return ans;
    }
}

LCP 50. 宝石补给(简单模拟)

https://leetcode.cn/problems/WHnhjV/?envType=daily-question&envId=2023-09-15
在这里插入图片描述

提示:
2 <= gem.length <= 10^3
0 <= gem[i] <= 10^3
0 <= operations.length <= 10^4
operations[i].length == 2
0 <= operations[i][0], operations[i][1] < gem.length

按照题意模拟即可,注意向下取整的用法。

class Solution {
    public int giveGem(int[] gem, int[][] operations) {
        // 模拟
        for (int[] op: operations) {
            gem[op[1]] += gem[op[0]] / 2;
            gem[op[0]] = (gem[op[0]] + 1) / 2;
        }
        int mn = gem[0], mx = gem[0];
        for (int g: gem) {
            mn = Math.min(mn, g);
            mx = Math.max(mx, g);
        }
        return mx - mn;
    }
}

198. 打家劫舍(经典线性DP)

https://leetcode.cn/problems/house-robber/?envType=daily-question&envId=2023-09-16
在这里插入图片描述
提示:
1 <= nums.length <= 100
0 <= nums[i] <= 400

经典线性规划嘛——
要么偷当前位置,要么不偷当前位置,取两者最大的。

class Solution {
    public int rob(int[] nums) {
        int n = nums.length;
        if (n == 1) return nums[0];
        int[] dp = new int[n];
        dp[0] = nums[0];
        dp[1] = Math.max(nums[0], nums[1]);
        for (int i = 2; i < n; ++i) dp[i] = Math.max(dp[i - 1], nums[i] + dp[i - 2]);
        return dp[n - 1];
    }
}

213. 打家劫舍 II(循环打家劫舍)

https://leetcode.cn/problems/house-robber-ii/description/?envType=daily-question&envId=2023-09-17
在这里插入图片描述

提示:
1 <= nums.length <= 100
0 <= nums[i] <= 1000

代码写法1——另写方法robR(l, r)

class Solution {
    public int rob(int[] nums) {
        int n = nums.length;
        if (n == 1) return nums[0];
        return Math.max(robR(nums, 0, n - 2), robR(nums, 1, n - 1));
    }

    public int robR(int[] nums, int l, int r) {
        if (l == r) return nums[l];
        int[] dp = new int[r - l + 1];
        dp[0] = nums[l];
        dp[1] = Math.max(dp[0], nums[l + 1]);
        for (int i = l + 2; i <= r; ++i) {
            dp[i - l] = Math.max(dp[i - 1 - l], dp[i - 2 - l] + nums[i]);
        }
        return dp[r - l];
    }
}

代码写法2——二维dp数组

class Solution {
    public int rob(int[] nums) {
        int n = nums.length;
        if (n == 1) return nums[0];
        int[] dp1 = new int[n], dp2 = new int[n];
        dp1[0] = nums[0];
        dp1[1] = Math.max(nums[0], nums[1]);
        dp2[1] = nums[1];
        for (int i = 2; i < n; ++i) {
            dp1[i] = Math.max(dp1[i - 1], dp1[i - 2] + nums[i]);
            dp2[i] = Math.max(dp2[i - 1], dp2[i - 2] + nums[i]);
        }
        return Math.max(dp1[n - 2], dp2[n - 1]);
    }
}

两种写法见仁见智吧。

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

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

相关文章

Java学习之常见易错点总结--第一期

&#x1f495;"不要同情自己&#xff0c;那是卑劣懦夫干的勾当。"&#x1f495; 作者&#xff1a;Mylvzi 文章主要内容&#xff1a;Java学习之常见易错点总结--第一期 1.什么时候变量不用初始化&#xff1f; 先来看如下代码&#xff1a; public static void main(…

MediaPipe+OpenCV 实现实时手势识别(附Python源码)

MediaPipe官网&#xff1a;https://developers.google.com/mediapipe MediaPipe仓库&#xff1a;https://github.com/google/mediapipe 一、MediaPipe介绍 MediaPipe 是一个由 Google 开发的开源跨平台机器学习框架&#xff0c;用于构建视觉和感知应用程序。它提供了一系列预训…

C#中Visual Studio如何为解决方案设置启动项目

目录 第一种方法:快速选定启动项目的方法1.在解决方案资源管理器中,选择解决方案(最高层节点)2.选择解决方案节点的上下文(右键单击)菜单,然后选择“属性”。 “解决方案属性页”对话框随即显示第二种方法:右击First11或者second11,点击设置启动项目即可Visual Studio…

C++ PrimerPlus 复习 第七章 函数——C++的编程模块(上)

第一章 命令编译链接文件 make文件 第二章 进入c 第三章 处理数据 第四章 复合类型 &#xff08;上&#xff09; 第四章 复合类型 &#xff08;下&#xff09; 第五章 循环和关系表达式 第六章 分支语句和逻辑运算符 第七章 函数——C的编程模块&#xff08;上&#xff…

【红包雨】中间件与环境安装

创建环境 创建专用网络VPC 安全组 创建云服务器 打包部署 2. Java环境 #下载jdk17 wget https://download.oracle.com/java/17/latest/jdk-17_linux-x64_bin.tar.gz #安装上传工具 以后使用命令 rz 选中文件进行上传 yum install -y lrzsz#解压 tar -xzvf jdk-17_linux-x64…

Hive参数与性能调优-V2.0

Hive作为大数据平台举足轻重的框架&#xff0c;以其稳定性和简单易用性也成为当前构建企业级数据仓库时使用最多的框架之一。 但是如果我们只局限于会使用Hive&#xff0c;而不考虑性能问题&#xff0c;就难搭建出一个完美的数仓&#xff0c;所以Hive性能调优是我们大数据从业…

VMware Fusion 13+Ubuntu ARM Server 22.04.3在M2芯片的Mac上共享文件夹

因为Server版没有桌面&#xff0c;VMware Tools不能直接装&#xff0c;导致没办法共享文件。 Ubuntu中的包如果需要更新&#xff0c;先执行下面的步骤 sudo apt update 再执行 sudo apt upgrade 不需要更新的话&#xff0c;直接执行下面的步骤 先把open-vm-tools卸载了 …

【JavaSE笔记】抽象类与接口

一、抽象类 1、概念 在面向对象的概念中&#xff0c;所有的对象都是通过类来描绘的&#xff0c;但是反过来&#xff0c;并不是所有的类都是用来描绘对象的&#xff0c;如果一个类中没有包含足够的信息来描绘一个具体的对象&#xff0c;这样的类就是抽象类。 package demo2…

React 开发一个移动端项目(2)

配置基础路由 目标&#xff1a;配置登录页面的路由并显示在页面中 步骤&#xff1a; 安装路由&#xff1a; yarn add react-router-dom5.3.0 5 和 6 两个版本对组件类型的兼容性和函数组件支持有所改变&#xff0c;在这里使用的是 5。 和路由的类型声明文件 yarn add types…

AI AIgents时代-(三.)AutoGPT和AgentGPT

前两篇讲解了Agent的原理和组件&#xff0c;这节我将给大家介绍两个agent项目&#xff0c;给出它们的工作原理和区别&#xff0c;并教大家亲手尝试使用 Agents&#x1f389; &#x1f7e2; AutoGPT&#x1f916;️ 我们的老朋友&#xff0c;之前文章也专门写过。AutoGPT 是一…

关于硬盘质量大数据分析的思考

近日&#xff0c;看到Backblaze分享了一遍关于硬盘运行监控数据架构的文章&#xff0c;觉得挺有意义的&#xff0c;本文就针对这方面跟大家聊聊。 作为一家在2021年在美国纳斯达克上市的云端备份公司&#xff0c;Backblaze一直保持着对外定期发布HDD和SSD的故障率稳定性质量报告…

中国智能客服发展历程

中国智能客服的发展历程&#xff1a; 在2000年以前&#xff0c;互联网尚未普及&#xff0c;客服主要以电话沟通为主。从2000年到2010年&#xff0c;得益于计算机技术、计算机电话集成技术&#xff08;CTI&#xff09;、网络技术、多媒体机技术以及CRM、BI、ERP、OA等企业信息化…

Centos7部署单机版MongoDB

目录 Centos7部署单机版MongoDBMongoDB介绍数据模型索引分布式高可用性查询语言驱动和社区用途缺点 下载并解压安装包创建相关文件夹和文件编辑mongod.conf文件启动mongodb创建管理员用户终止MongoDB服务配置自启动服务关闭SELinux编辑自启动服务文件mongodb服务命令 Centos7部…

Primer.ai:分析总结并生成报告

【产品介绍】 名称 Primer.ai 上线时间 成立时间:2015年 具体描述 Primer.ai是一个新兴的人工智能企业&#xff0c;帮助用户处理大量文本数据存储。它使用机器学习技术帮助解析。Primer平台使用机器学习和自然语言处理来构建能够阅读文档、开发见解和生…

数据结构——散列函数、散列表

文章目录 前言一、散列表的基本概念二、散列函数的构造方法三、处理冲突的方法1. 开放定址法&#xff1a;2. 拉链法 四、散列查找及性能分析总结 前言 散列表的基本概念散列函数的构造方法处理冲突的方法散列查找及性能分析 提示&#xff1a;以下是本篇文章正文内容&#xff0…

C【动态内存管理】

1. 为什么存在动态内存分配 int val 20;//在栈空间上开辟四个字节 char arr[10] {0};//在栈空间上开辟10个字节的连续空间 2. 动态内存函数的介绍 2.1 malloc&#xff1a;stdlib.h void* malloc (size_t size); int* p (int*)malloc(40); #include <stdlib.h> #incl…

基于 kubernetes+docker构建高可用、高性能的 web 、CICD集群

文章目录 一、项目架构图二 、项目描述三、项目环境四、环境准备1、IP地址规划2、关闭selinux和firewall3、配置静态ip地址4、修改主机名5、升级系统&#xff08;可做可不做&#xff09;6、添加hosts解析 五、项目步骤1、设计整个集群的架构&#xff0c;规划好服务器的IP地址&a…

# 数据库开发-MySQL基础DDL-DML总结

数据库&#xff1a;英文为 DataBase&#xff0c;简称DB&#xff0c;它是存储和管理数据的仓库。 数据库管理系统&#xff08;DataBase Management System&#xff0c;简称DBMS&#xff09; DBMS是操作和管理数据库的大型软件。将来我们只需要操作这个软件&#xff0c;就可以通…

Proteus的编译运行(以AT89C51为例)

最近&#xff0c;突然又用到了Proteus,之前还是大三上的时候上微机原理的时候用到过&#xff0c;今天记录一下如何在Proteus中编写代码&#xff0c;编译运行。 首先&#xff0c;选中AT89C51芯片&#xff0c;右键选择编辑源代码。 选择芯片的系列与对应的编译器&#xff0c;这里…

正确理解芯片解密,解除偏见

正确理解芯片解密&#xff0c;解除偏见 电子半导体技术在当今时代如日中天&#xff0c;许多行业都有着它的应用&#xff0c;芯片解密也不例外。那么什么是芯片解密&#xff1f;芯片解密是一种新兴的逆向工程技术&#xff0c;它利用半导体逆向技术来解密加密后的芯片&#xff0c…