2023.07.08力扣6题

news2024/9/22 15:28:37

在这里插入图片描述

167. 两数之和 II - 输入有序数组

给你一个下标从 1 开始的整数数组 numbers ,该数组已按 非递减顺序排列 ,请你从数组中找出满足相加之和等于目标数 target
的两个数。如果设这两个数分别是 numbers[index1] 和 numbers[index2] ,则 1 <= index1 <
index2 <= numbers.length 。

以长度为 2 的整数数组 [index1, index2] 的形式返回这两个整数的下标 index1 和 index2。

你可以假设每个输入 只对应唯一的答案 ,而且你 不可以 重复使用相同的元素。

你所设计的解决方案必须只使用常量级的额外空间。

示例 1:

输入:numbers = [2,7,11,15], target = 9
输出:[1,2]
解释:2 与 7 之和等于目标数 9 。因此 index1 = 1, index2 = 2 。返回 [1, 2] 。
示例 2:

输入:numbers = [2,3,4], target = 6
输出:[1,3]
解释:2 与 4 之和等于目标数 6 。因此 index1 = 1, index2 = 3 。返回 [1, 3] 。
示例 3:

输入:numbers = [-1,0], target = -1
输出:[1,2]
解释:-1 与 0 之和等于目标数 -1 。因此 index1 = 1, index2 = 2 。返回 [1, 2] 。

两种方法:O(n)双指针法和O(nlogn)的二分查找法

//方法二:双指针法 O(n)
class Solution {
    public int[] twoSum(int[] numbers, int target) {
        int[] res = new int[2];
        int left=0,right=numbers.length-1;
        while(left<right){
            if(numbers[left]+numbers[right]<target) left++;
            else if(numbers[left]+numbers[right]>target) right--;
            else {
                res[0]=left+1;
                res[1]=right+1;
                break;
            }
        }
        return res;
    }


//方法一:O(nlogn) 二分查找
    public int[] twoSum(int[] numbers, int target) {
        int[] res = new int[2];
        int key=0;
        //思路是:双指针/二分查找/数组
        for(int i=0;i<numbers.length-1;i++){
            key=target-numbers[i];
            //二分查找
            int index=binarySearch(numbers,key,i+1,numbers.length-1);
            if(index==-1) continue;
            else{
                res[0]=i+1;
                res[1]=index+1;
                break;
            }
        }
        return res;
    }

    int binarySearch(int[] numbers, int key, int left, int right) {
        if(left>right) return -1;
        int mid=(right+left)/2;
        if(numbers[mid]>key) return binarySearch(numbers, key, left, mid-1);
        else if(numbers[mid]==key) return mid;
        else return binarySearch(numbers, key, mid+1, right);
    }
}

Khan拓扑排序算法

207. 课程表

你这个学期必须选修 numCourses 门课程,记为 0 到 numCourses - 1 。

在选修某些课程之前需要一些先修课程。 先修课程按数组 prerequisites 给出,其中 prerequisites[i] = [ai,
bi] ,表示如果要学习课程 ai 则 必须 先学习课程 bi 。

例如,先修课程对 [0, 1] 表示:想要学习课程 0 ,你需要先完成课程 1 。 请你判断是否可能完成所有课程的学习?如果可以,返回
true ;否则,返回 false 。

示例 1:

输入:numCourses = 2, prerequisites = [[1,0]]
输出:true
解释:总共有 2 门课程。学习课程 1 之前,你需要完成课程 0 。这是可能的。

示例 2:

输入:numCourses = 2, prerequisites = [[1,0],[0,1]]
输出:false
解释:总共有 2 门课程。学习课程 1 之前,你需要先完成​课程 0 ;并且学习课程 0 之前,你还应先完成课程 1 。这是不可能的。
 

提示:

1 <= numCourses <= 105
0 <= prerequisites.length <= 5000
prerequisites[i].length == 2
0 <= ai, bi < numCourses
prerequisites[i] 中的所有课程对 互不相同
class Solution {
    public boolean canFinish(int numCourses, int[][] prerequisites) {
        /*
        统计每个课被指向次数,初始被指向次数为0的肯定是安全的(不在环上)。
        每被安全课程指向一次,被指次数减一,
        如果被指次数减到0,说明该课程全部指向都来自安全课程,则它也是安全的。
        依此进行队列循环。
拓扑排序不用区分什么广度优先深度优先把自己弄乱了,抓住节点入度和出度的本质特征。 方法一: 从入度思考(从前往后排序), 入度为0的节点在拓扑排序中一定排在前面, 然后删除和该节点对应的边, 迭代寻找入度为0的节点。 方法二: 从出度思考(从后往前排序), 出度为0的节点在拓扑排序中一定排在后面, 然后删除和该节点对应的边, 迭代寻找出度为0的节点。
        */
        int[] point=new int[numCourses];  //记录每个课程被指向的次数
        int len=prerequisites.length;
        for(int[] p:prerequisites){
            point[p[0]]++;
        }
        boolean[] removed=new boolean[len];
        int remove=0;
        while(remove<len){
            int currentRemove=0;
            for(int i=0;i<len;i++){
                if(removed[i]) continue;  //该规则已被删除
                int[] p=prerequisites[i]; 
                if(point[p[1]]==0){       //判断指向课程的是否为安全课程,是的话就可以删除该规则。
                    point[p[0]]--;
                    removed[i]=true;
                    currentRemove++;
                }
            }
            if(currentRemove==0) return false; // 如果一轮跑下来一个元素都没移除,则没必要进行下一轮
            remove+=currentRemove;
        }
        return true;
    }
}

210. 课程表 II

现在你总共有 numCourses 门课需要选,记为 0 到 numCourses - 1。给你一个数组 prerequisites ,其中
prerequisites[i] = [ai, bi] ,表示在选修课程 ai 前 必须 先选修 bi 。

例如,想要学习课程 0 ,你需要先完成课程 1 ,我们用一个匹配来表示:[0,1] 。
返回你为了学完所有课程所安排的学习顺序。可能会有多个正确的顺序,你只要返回 任意一种 就可以了。如果不可能完成所有课程,返回 一个空数组 。

示例 1:

输入:numCourses = 2, prerequisites = [[1,0]]
输出:[0,1]
解释:总共有 2 门课程。要学习课程 1,你需要先完成课程 0。因此,正确的课程顺序为 [0,1] 。
示例 2:

输入:numCourses = 4, prerequisites = [[1,0],[2,0],[3,1],[3,2]]
输出:[0,2,1,3]
解释:总共有 4 门课程。要学习课程 3,你应该先完成课程 1 和课程 2。并且课程 1 和课程 2 都应该排在课程 0 之后。
因此,一个正确的课程顺序是 [0,1,2,3] 。另一个正确的排序是 [0,2,1,3] 。
示例 3:

输入:numCourses = 1, prerequisites = []
输出:[0]
 

提示:
1 <= numCourses <= 2000
0 <= prerequisites.length <= numCourses * (numCourses - 1)
prerequisites[i].length == 2
0 <= ai, bi < numCourses
ai != bi
所有[ai, bi] 互不相同
class Solution {
    public int[] findOrder(int numCourses, int[][] prerequisites) {
        int[] res=new int[numCourses];  //记录返回的课程学习顺序
        int index=0;
        int[] point=new int[numCourses]; //记录每个课程的入度,入度为0的时候是安全课程可以进行学习
        for(int[] p:prerequisites){
            point[p[0]]++;
        }
        for(int i=0;i<numCourses;i++){
            if(point[i]==0){
                res[index++]=i;
            }
        }
        int len=prerequisites.length;
        boolean[] removed=new boolean[len];
        int remove=0;
        while(remove<len){
            int currentRemove=0;
            for(int i=0;i<len;i++){
                if(removed[i]) continue;
                int[]p =prerequisites[i];
                if(point[p[1]]==0){
                    point[p[0]]--;
                    removed[i]=true;
                    currentRemove++;
                    if(point[p[0]]==0) res[index++]=p[0];
                }
            }
            if(currentRemove==0){
                return new int[0];
            }
            remove+=currentRemove;
        }
        return res;
    }
}

拓扑排序算法重点看入度,入度为0可以放入队列中,然后依次取出队列中元素,切断该元素与后续元素的连接,即相关元素的入度全部-1,同时判断入度是否为0,为0则进入队列。循环进行取队列中元素...

236. 二叉树的最近公共祖先

给定一个二叉树, 找到该树中两个指定节点的最近公共祖先。

百度百科中最近公共祖先的定义为:“对于有根树 T 的两个节点 p、q,最近公共祖先表示为一个节点 x,满足 x 是 p、q 的祖先且 x
的深度尽可能大(一个节点也可以是它自己的祖先)。”

示例 1:
在这里插入图片描述

输入:root = [3,5,1,6,2,0,8,null,null,7,4], p = 5, q = 1
输出:3
解释:节点 5 和节点 1 的最近公共祖先是节点 3

示例 2:
在这里插入图片描述

输入:root = [3,5,1,6,2,0,8,null,null,7,4], p = 5, q = 4
输出:5
解释:节点 5 和节点 4 的最近公共祖先是节点 5 。因为根据定义最近公共祖先节点可以为节点本身。

提示:

树中节点数目在范围 [2, 105] 内。
-109 <= Node.val <= 109
所有 Node.val 互不相同 。
p != q
p 和 q 均存在于给定的二叉树中。

根据以上定义,若 root 是 p,q 的 最近公共祖先 ,则只可能为以下情况之一:
p 和 q 在 root 的子树中,且分列 root 的 异侧(即分别在左、右子树中);
p=root ,且 q 在 root 的左或右子树中;
q=root ,且 p 在 root的左或右子树中;

在这里插入图片描述

考虑通过递归对二叉树进行先序遍历,当遇到节点 p 或 q 时返回。从底至顶回溯,当节点 p,q, 在节点root的异侧时,节点 root即为最近公共祖先,则向上返回 root 。

递归解析: 终止条件: 当越过叶节点,则直接返回 null; 当 root等于 p,q,则直接返回 root; 递推工作: 开启递归左子节点,返回值记为 left;开启递归右子节点,返回值记为 right; 返回值: 根据 left和 right,可展开为四种情况; 当 left和 right同时为空 :说明root的左 / 右子树中都不包含 p,q ,返回 null; 当 left和right同时不为空 :说明 p,q 分列在 root 的 异侧 (分别在 左 / 右子树),因此 root为最近公共祖先,返回 root; 当 left为空,right不为空 :p,q 都不在 root的左子树中,直接返回right 。具体可分为两种情况: p,q 其中一个在 root 的 右子树 中,此时right 指向 p(假设为 p ); p,q 两节点都在root 的 右子树中,此时的right 指向 最近公共祖先节点 ; 当 left 不为空,right 为空 :与情况 3. 同理;

class Solution {
    public TreeNode lowestCommonAncestor(TreeNode root, TreeNode p, TreeNode q) {
        //二叉树的深度优先搜索dfs,可以用栈完成
        if(root==null||root==p||root==q) return root;
        TreeNode left=lowestCommonAncestor(root.left,p,q);
        TreeNode right=lowestCommonAncestor(root.right,p,q);
        if(left!=null&&right!=null) return root;
        if(left!=null) return left;
        return right;
    }
}

在这里插入图片描述

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

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

相关文章

Carla与Ros联合仿真教学与踩坑经历

Carla与Ros联合仿真教学与踩坑经历 前言 本人需要用到carla进行仿真&#xff0c;做实验&#xff0c;研究了这个平台几个月。 需要注意的是&#xff0c;本人没有保留所有的ros包&#xff0c;而是选择一些进行使用&#xff0c;其他大家可以进行扩展。 carla0.9.5版本和carla0.…

雅思口语考试的顺序与技巧?

雅思口语的考试顺序&#xff0c;也是学生们在开始考试前要了解的信息。雅思的口语考试到底有怎样的考试顺序&#xff1f;下面就听小编讲讲它的考试顺序&#xff0c;以及考试中的技巧。 一、雅思口试考试顺序 众所周知&#xff0c;雅思考试分为笔试和口试。正常情况下&#xff…

YOLOV5-Lite轻量化部署与训练

文章目录 前言项目下载项目运行自定义数据集训练使用LabelImg标注制作数据集划分训练文件生成标签聚合操作辅助脚本需要运行的脚本 开始训练 总结 前言 没啥意思&#xff0c;很简单&#xff0c;需要实现一个目标检测&#xff0c;但是&#xff0c;不能占用太多运算资源&#xf…

【双指针】977. 有序数组的平方

977. 有序数组的平方 解题思路 思路: 设置前后指针最大的元素一定是存在再前后位置,然后因为负数平方之后可能大于整数的平方每次比较前后指针指向的元素的平方 然后存下较大的元素平方 然后移动指针 class Solution {public int[] sortedSquares(int[] nums) {// 设置前后指…

Git--远程操作

文章目录 前言一、理解分布式版本控制系统二、远程仓库1.新建远程仓库2.克隆远程仓库3.向远程仓库推送4.拉取远程仓库5.配置Git忽略特殊文件 给命令配置别名 总结 前言 正文开始!!! 一、理解分布式版本控制系统 我们目前所说的所有内容(工作区,暂存区,版本库等等),都是在本地…

scratch角色跟随

scratch 角色跟随 本程序实现了角色跟随功能&#xff0c;第一个角色面向鼠标指针&#xff0c;其它角色面向前一个角色&#xff0c;在距离较小时暂停。 5个角色的程序依次为&#xff1a;

RegNeRF,FreeNeRF: 神经辐射场的自由频率正则化,几何正则化,外观正则化,遮挡正则化

目录 概要&#xff1a; 一 论文 RegNeRF: Regularizing Neural Radiance Fields for View Synthesis from Sparse Inputs 1.几何正则化 2.外观正则化 二 论文 FreeNeRF: Improving Few-shot Neural Rendering with Free Frequency Regularization 3 频率正则化 和自由频…

155 mini_stack

Title Description 155. 最小栈 - 力扣&#xff08;Leetcode&#xff09; resolvent 觉得比较困难的地方就是在minstack那个部分: 两个创新点: 1.使用了INTMAX防止存放有效避免指针的问题 2.使用了min_stack时间换空间 class MinStack { public:stack<int> stack1;s…

ChatGPT带我做四轴飞行器和自平衡小车

按照ChatGPT的说法&#xff0c;这款主板的的主控MCU、无线通信、电源管理、外设接口可以共用&#xff0c;需要差异化的有电机驱动、传感器的选择、控制算法和软件、电源供电。ChatGPT说的共用部分没啥争议&#xff0c;有差异化的地方需要细想下&#xff1a;电机驱动显然应该不同…

three.jsgsap滚动交互网页实现 2-创建文字并添加离开动画

添加动画 让聚光灯的角度随着下滑增大&#xff0c;展示完整的场景 const container document.querySelector("#container");gsap.to(light, {angle: 0.7,scrollTrigger: {trigger: container,start: 0,end: innerHeight,scrub: 1},});这样下滑一个屏幕高度聚光灯的角…

Redis——初窥门径

前言 在这篇文章中&#xff0c;荔枝整理了初步了解Redis的一些基础知识和常见指令。通过这篇文章我们可以弄懂Redis具体是什么以及主要的功能、基本数据类型和操作指令。这里注意如果标题后面带*则是仅需要了解就行的知识点哈。 文章目录 前言 一、Redis概述和配置 1.1 概述…

Android Compose UI实战练手----Google Bloom 主页实现(完结)

目录 1.概述2.页面展示2.1 亮色主题2.2 深色主题 3.页面拆分及实现3.1 主页的UI整体UI架构实现3.2 底部导航栏BottomBar的实现3.3 搜索栏SearchBar的实现3.4 Banner实现3.5 中间信息列表BloomInfoList的实现 4.源码地址 1.概述 主页的页面比前面的欢迎页和登录页面要复杂得多&…

Microsoft Visual Studio 2022添加.NET Framework 4.6.2框架,然后说下.NET目标包的作用。

众所周知&#xff0c;Microsoft Visual Studio 2022不再支持.NET Framework 4.6以下的框架。从而导致前期使用老框架开发的某些应用无法打开&#xff08;打开时提示安装框架&#xff0c;但又安装不成功&#xff09;的情况出现。 前于如何安装.NET Framework 4.5及更早版本框架的…

Java中的字符串类

提示&#xff1a;字符串类是编程中最常用的一种数据类型&#xff0c;比较重要❗ 文章目录 前言一、字符串类创建对象方式静态创建动态创建 二、String字符串内容不可改变三、字符串常用方法length方法charAt方法substring方法indexOf与lastIndexOfindexOf方法lastIndexOf方法 替…

计算机基础--->数据结构(9)【并查集】

文章目录 并查集的概述并查集的主要用途并查集的实现创建和初始化集合查找当前元素的集合根节点判断两个元素是否处于同一集合合并两个集合对节点的路径进行压缩 并查集的概述 并查集是一种用于解决集合合并和查询问题的数据结构&#xff0c;主要用于实现有关集合的操作&#x…

Skywalking高级使用

Skywalking高级使用 RPC调用监控Mysql调用监控Skywalking常用插件获取追踪ID过滤指定的端点告警功能Skywalking原理Open Tracing介绍 RPC调用监控 Skywalking(6.5.0)支持的RPC框架有以下几种&#xff1a; (1) Dubbo 2.5.4 -> 2.6.0 (2) Dubbox 2.8.4 (3) Apache Dubbo 2.7.…

动态规划 DP (六) 字符串编辑

1.字符串编辑 字符串编辑问题是一类常见的问题&#xff0c;通常涉及对字符串进行插入、删除、替换等操作&#xff0c;以达到某种特定的目标。 常见的字符串编辑问题包括&#xff1a; 编辑距离&#xff08;Edit Distance&#xff09;&#xff1a;给定两个字符串&#xff0c;通…

最新抖音娱乐测评小程序源码 Thinkphp后端 抖音引流小程序

最新抖音娱乐测评小程序源码 thinkphp后端 抖音引流小程序 附搭建教程 测试环境 NginxPHP7.0MySQL5.6 网站运行目录设置为 /web 数据库配置文件 \source\application\database.php 后台登录地址 http://你的域名/index.php?s/admin/passport/login

python环境

卸载旧环境 wini 打开应用卸载 删除python解释器和pycharm 删除配置文件夹JetBrains C:\Users\CJC\AppData\Roaming\JetBrains 安装 安装python解释器 安装pycharm 查看或设置该项目的解释器和安装包 快捷键 全局搜索 双击shift 当前文件中搜索 ctrl f 查看函数…

MySQL数据库对象与数据备份和还原详解

目录 一、视图 1. 什么是视图 2. 视图与数据表的区别 3. 视图的优点 4. 创建视图 二、索引 1. 什么是索引 2. 为什么要使用索引 3. 索引优缺点 4. 何时不使用索引 5. 索引何时失效 6. 索引分类 6.1 普通索引 6.2 唯一索引 6.3 主键索引 6.4 组合索引 三、数据的…