2023.07.13力扣6题

news2024/9/26 1:19:00

931. 下降路径最小和

给你一个 n x n 的 方形 整数数组 matrix ,请你找出并返回通过 matrix 的下降路径 的 最小和 。

下降路径可以从第一行中的任何元素开始,并从每一行中选择一个元素。在下一行选择的元素和当前行所选元素最多相隔一列(即位于正下方或者沿对角线向左或者向右的第一个元素)。具体来说,位置(row, col) 的下一个元素应当是 (row + 1, col - 1)、(row + 1, col) 或者 (row + 1, col + 1) 。

示例 1

在这里插入图片描述

输入:matrix = [[2,1,3],[6,5,4],[7,8,9]]
输出:13
解释:如图所示,为和最小的两条下降路径

示例 2

在这里插入图片描述

输入:matrix = [[-19,57],[-40,-5]]
输出:-59
解释:如图所示,为和最小的下降路径
 

提示:

n == matrix.length == matrix[i].length
1 <= n <= 100
-100 <= matrix[i][j] <= 100

dp[i][j]=min(dp[i-1][j-1],dp[i-1][j],dp[i-1][j+1])

class Solution {
    public int minFallingPathSum(int[][] matrix) {
       //d[i][j]=min(d[i-1][j-1],d[i-1][j],d[i-1][j+1])+matrix[i][j]
        int ans=Integer.MAX_VALUE;
        int n=matrix.length;
        int[][] dp=new int[n][n];
        if(n==1) return matrix[0][0];
        for(int i=0;i<n;i++) {
            dp[0][i] = matrix[0][i];
        }
        for(int i=1;i<n;i++){
            for(int j=0;j<n;j++){
                if(j==0){
                    dp[i][j]=Math.min(dp[i-1][j],dp[i-1][j+1]);
                }else if(j==n-1){
                    dp[i][j]=Math.min(dp[i-1][j-1],dp[i-1][j]);
                }else{
                    dp[i][j]=Math.min(Math.min(dp[i-1][j-1],dp[i-1][j]),dp[i-1][j+1]);
                }
                dp[i][j]+=matrix[i][j];
                if(i==n-1){
                    ans=Math.min(ans,dp[i][j]);
                }
            }
        }
        return ans;
    }
}

979. 在二叉树中分配硬币

给定一个有 N 个结点的二叉树的根结点 root,树中的每个结点上都对应有 node.val 枚硬币,并且总共有 N 枚硬币。

在一次移动中,我们可以选择两个相邻的结点,然后将一枚硬币从其中一个结点移动到另一个结点。(移动可以是从父结点到子结点,或者从子结点移动到父结点)。

返回使每个结点上只有一枚硬币所需的移动次数。

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


输入:[3,0,0]
输出:2
解释:从树的根结点开始,我们将一枚硬币移到它的左子结点上,一枚硬币移到它的右子结点上。

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

输入:[0,3,0]
输出:3
解释:从根结点的左子结点开始,我们将两枚硬币移到根结点上 [移动两次]。然后,我们把一枚硬币从根结点移到右子结点上。

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

输入:[1,0,2]
输出:2

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

输入:[1,0,0,null,3]
输出:4
 
提示:

1<= N <= 100
0 <= node.val <= N

581. 最短无序连续子数组

给你一个整数数组 nums ,你需要找出一个 连续子数组 ,如果对这个子数组进行升序排序,那么整个数组都会变为升序排序。

请你找出符合题意的 最短 子数组,并输出它的长度。

示例 1:

输入:nums = [2,6,4,8,10,9,15]
输出:5
解释:你只需要对 [6, 4, 8, 10, 9] 进行升序排序,那么整个表都会变为升序排序。

示例 2:

输入:nums = [1,2,3,4]
输出:0

示例 3:

输入:nums = [1]
输出:0
 
提示:

1 <= nums.length <= 104
-105 <= nums[i] <= 105
 
进阶:你可以设计一个时间复杂度为 O(n) 的解决方案吗?

方法一:时间复杂度O(n^2)

public static int findUnsortedSubarray(int[] nums) {
        //从左侧开始遍历找第一个存在右侧元素大于它的,它便为升序排序最左侧元素
        //再从右侧开始遍历找第一个存在左侧元素小于它的,它便为升序排序最右侧元素
        int n=nums.length;
        int indexLeft=-1,indexRight=n;
        for(int i=0;i<n-1;i++){
            for(int j=i+1;j<n;j++){
                if(nums[i]>nums[j]){
                    indexLeft=i;
                    break;
                }
            }
            if(indexLeft!=-1){
                break;
            }
        }
        //原序列已经是个升序序列
        if(indexLeft==-1){
            return 0;
        }
        for(int i=n-1;i>0;i--){
            for(int j=i-1;j>=0;j--){
                if(nums[i]<nums[j]){
                    indexRight=i;
                    break;
                }
            }
            if(indexRight!=n){
                break;
            }
        }
        return indexRight-indexLeft+1;
    }

方法二:时间复杂度O(n)

我提供一个我的理解(有点贪心的感觉):

首先,我们希望这个数组是单调递增的(不是严格单调递增,相邻可以相等)
从左往右,一开始max是第一个数。如果数组符合要求,那么遍历的每一个数都只会相等或者越来越大,也就是我们只会不停地更新max的值。但是,一旦碰到一个小于max的数,就说明这个数字的位置不对,这个数字一定是在我们最终要重新sort的subarray里的,并且是右边界(因为我们在不断向右探索)。
从右往左同理,只是大小关系反一反,我们能找到需要重新sort的subarray的左边界。

这样就找到答案了。

法二的理解

从左往右遍历,遍历到i,max记录的是从0到i最大的数,如果第i个位置比max小,证明第i位置元素处在一个不正确的位置(因为它前面有个比它大的数),记录下标high。

从右往左遍历,遍历到i,min记录的是从末尾元素到i元素最小的数,如果第i位置元素比min大了,证明第i位置元素也处在一个不正确的位置(因为它后面有比它小的数),记录下标low。

计算两个不正确的位置low和high之间的距离。

public static int findUnsortedSubarray(int[] nums) {
        //单调栈,或者也可以不用单调栈,直接用两个数max和min去维护
        int n=nums.length;
        int indexLeft=-1,indexRight=n;
        Deque<Integer> deque=new ArrayDeque<>();
        deque.addFirst(0);
        for(int i=1;i<n;i++){
            if(!deque.isEmpty()&&nums[i]>nums[deque.getLast()]) deque.addLast(i);
            if(!deque.isEmpty()&&nums[i]<nums[deque.getLast()]){
                indexRight=i;
            }
        }
        deque.clear();
        deque.addFirst(n-1);
        for(int i=n-2;i>=0;i--){
            if(!deque.isEmpty()&&nums[i]<nums[deque.getLast()]) deque.addLast(i);
            if(!deque.isEmpty()&&nums[i]>nums[deque.getLast()]){
                indexLeft=i;
            }
        }
        if(indexLeft==-1||indexRight==n) return 0;
        return indexRight-indexLeft+1;
    }

2208. 将数组和减半的最少操作次数

给你一个正整数数组 nums 。每一次操作中,你可以从 nums 中选择 任意 一个数并将它减小到 恰好
一半。(注意,在后续操作中你可以对减半过的数继续执行操作)

请你返回将 nums 数组和 至少 减少一半的 最少 操作数。

示例 1:

输入:nums = [5,19,8,1]
输出:3
解释:初始 nums 的和为 5 + 19 + 8 + 1 = 33 。
以下是将数组和减少至少一半的一种方法:
选择数字 19 并减小为 9.5 。
选择数字 9.5 并减小为 4.75 。
选择数字 8 并减小为 4 。
最终数组为 [5, 4.75, 4, 1] ,和为 5 + 4.75 + 4 + 1 = 14.75 。
nums 的和减小了 33 - 14.75 = 18.25 ,减小的部分超过了初始数组和的一半,18.25 >= 33/2 = 16.5 。
我们需要 3 个操作实现题目要求,所以返回 3 。
可以证明,无法通过少于 3 个操作使数组和减少至少一半。

示例 2:

输入:nums = [3,8,20]
输出:3
解释:初始 nums 的和为 3 + 8 + 20 = 31 。
以下是将数组和减少至少一半的一种方法:
选择数字 20 并减小为 10 。
选择数字 10 并减小为 5 。
选择数字 3 并减小为 1.5 。
最终数组为 [1.5, 8, 5] ,和为 1.5 + 8 + 5 = 14.5 。
nums 的和减小了 31 - 14.5 = 16.5 ,减小的部分超过了初始数组和的一半, 16.5 >= 31/2 = 16.5 。
我们需要 3 个操作实现题目要求,所以返回 3 。
可以证明,无法通过少于 3 个操作使数组和减少至少一半。
 
提示:

1 <= nums.length <= 105
1 <= nums[i] <= 107

采用java中自带的接口优先队列:PriorityQueue,其内部是默认小根堆存储的,可以根据需求更改成大根堆

class Solution {
    public int halveArray(int[] nums) {
        int res = 0;
        double sum = 0, subNum = 0;
        PriorityQueue<Double> priorityQueue = new PriorityQueue<>(Collections.reverseOrder());  //默认小根堆,本题需要使用的是大根堆
        for (int num : nums) {
            sum += num;
            priorityQueue.offer(num * 1.0);
        }
        sum = sum / 2.0;
        while(subNum<sum){
            double n=priorityQueue.poll();
            subNum+=n/2.0;
            priorityQueue.offer(n/2.0);
            res++;
        }
        return res;
    }
}

141. 环形链表

给你一个链表的头节点 head ,判断链表中是否有环。

如果链表中有某个节点,可以通过连续跟踪 next 指针再次到达,则链表中存在环。 为了表示给定链表中的环,评测系统内部使用整数 pos来表示链表尾连接到链表中的位置(索引从 0 开始)。注意:pos 不作为参数进行传递 。仅仅是为了标识链表的实际情况。

如果链表中存在环 ,则返回 true 。 否则,返回 false 。

在这里插入图片描述

输入:head = [3,2,0,-4], pos = 1
输出:true
解释:链表中有一个环,其尾部连接到第二个节点。

在这里插入图片描述

输入:head = [1,2], pos = 0
输出:true
解释:链表中有一个环,其尾部连接到第一个节点。

在这里插入图片描述

输入:head = [1], pos = -1
输出:false
解释:链表中没有环。

提示:

链表中节点的数目范围是 [0, 104]
-105 <= Node.val <= 105
pos 为 -1 或者链表中的一个 有效索引 。

法一:简单但是耗费内存,内存为O(n)

public boolean hasCycle(ListNode head) {
        //断链法
        List<ListNode> list=new ArrayList<>();
        ListNode node=head,nodeNext=null;
        while(node!=null){
            nodeNext=node.next;
            node.next=null;
            if(list.contains(node)) {
                return true;
            }
            list.add(node);
            node=nodeNext;
        }
        return false;
    }

法二:快慢指针法,经典解决链表中有环的问题

public boolean hasCycle(ListNode head) {
        //追赶法--->快慢指针法,两个指针都在环里面的时候相差一个环那么多的时候一定会相遇
        //并且快指针比慢指针每次多走一步,所以一定会相遇
        ListNode fast=head,slow=head;
        while(fast!=null&&fast.next!=null){  //不用管slow,fast永远在它前面保驾护航
            fast=fast.next.next;  //兔子走两步
            slow=slow.next;       //乌龟走一步
            if(fast==slow) return true;  //相遇
        }
        return false;    //没有环
    }

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

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

相关文章

Python批量将Excel内指定列的数据向上移动一行

本文介绍基于Python语言&#xff0c;针对一个文件夹下大量的Excel表格文件&#xff0c;对其中的每一个文件加以操作——将其中指定的若干列的数据部分都向上移动一行&#xff0c;并将所有操作完毕的Excel表格文件中的数据加以合并&#xff0c;生成一个新的Excel文件的方法。 首…

走进Linux世界【七、Linux网络及快照和克隆】

Linux系统学习 走进Linux世界【一、Linux概述】 走进Linux世界【二、VM与Linux安装】 走进Linux世界【三、Linux文件与路径】 走进Linux世界【四、Linux基本命令一】 走进Linux世界【五、Linux基本命令二】 走进Linux世界【六、Linux编辑器vim】 走进Linux世界【七、Lin…

Nest grpc 实践之调用 python ddddocr 库

我曾经写过一个项目 ddddocr_server&#xff0c;使用 fastapi 提供 http 接口&#xff0c;以此来调用 ddddocr 库。 其他语言想要调用的话&#xff0c;则是通过 http 协议的方式来调用。然而 http 协议的开销不小&#xff0c;而 Websocket 调用又不灵活&#xff0c;此时针对这…

【计网】TCP在可靠传输中都干了啥

文章目录 1、概述2、校验和3、序列号和确认应答机制4、重传机制4.1、介绍4.2、超时重传4.3、快速重传 5、滑动窗口协议5.1、介绍5.2、发送方的滑动窗口5.3、接收方的滑动窗口 6、流量控制7、拥塞控制7.1、介绍7.2、慢开始7.3、拥塞避免7.4、快重传和快恢复 1、概述 TCP 是面向…

Day45 算法记录| 动态规划 12

股票问题 309. 买卖股票的最佳时机含冷冻期714.买卖股票的最佳时机含手续费 309. 买卖股票的最佳时机含冷冻期 这个视频讲解的很好 309.最佳买卖股票时机含冷冻期 class Solution {public int maxProfit(int[] prices) {int day prices.length;int [][] dp new int[day][2…

【雕爷学编程】MicroPython动手做(14)——掌控板之OLED屏幕

知识点&#xff1a;什么是掌控板&#xff1f; 掌控板是一块普及STEAM创客教育、人工智能教育、机器人编程教育的开源智能硬件。它集成ESP-32高性能双核芯片&#xff0c;支持WiFi和蓝牙双模通信&#xff0c;可作为物联网节点&#xff0c;实现物联网应用。同时掌控板上集成了OLED…

IOS UICollectionView 设置cell大小不生效问题

代码设置flowLayout.itemSize 单元格并没有改变布局大小&#xff0c; 解决办法如下图&#xff1a;把View flow layout 的estimate size 设置为None&#xff0c;上面设置的itemSize 生效了。

【Spring Boot】实战:实现优雅的数据返回

实战&#xff1a;实现优雅的数据返回 本节介绍如何让前后台优雅地进行数据交互&#xff0c;正常的数据如何统一数据格式&#xff0c;以及异常情况如何统一处理并返回统一格式的数据。 1.为什么要统一返回值 在项目开发过程中经常会涉及服务端、客户端接口数据传输或前后台分…

不同路径 II

一个机器人位于一个 m x n 网格的左上角 &#xff08;起始点在下图中标记为 “Start” &#xff09;。 机器人每次只能向下或者向右移动一步。机器人试图达到网格的右下角&#xff08;在下图中标记为 “Finish”&#xff09;。 现在考虑网格中有障碍物。那么从左上角到右下角…

Android 面试题 ANR 五

&#x1f525; 什么是 ANR &#x1f525; ANR(Application Not Responding )应用无响应的简称&#xff0c;是为了在 APP卡死时&#xff0c;用户 可以强制退出APP的选择&#xff0c;从而避免卡机无响应问题&#xff0c;这是Android系统的一种自我保护机制。 在Android中&#xf…

Vue基础 --- 动态组件 插槽 自定义指令

1. 动态组件 1.1 什么是动态组件 动态组件指的是动态切换组件的显示与隐藏。 1.2 如何实现动态组件渲染 vue 提供了一个内置的 <component> 组件&#xff0c;专门用来实现动态组件的渲染。示例代码如下&#xff1a; data() { <!-- 1.当前要渲染的组件名称 -->…

ad+硬件每日学习十个知识点(13)23.7.24(MOS管纠错!!!)

1.MOS管到底怎么接&#xff1f;&#xff08;我一直都错了&#xff09; 2.MOS管的非饱和区 答&#xff1a; 3.MOS管的饱和区 答&#xff1a; 4.MOS管的截止区和击穿区 答&#xff1a; 5.做开关&#xff0c;让三极管工作在饱和区&#xff0c;让MOS管工作在非饱和区&…

rocketmq rsqldb 简单记录

GitHub 地址 https://github.com/alibaba/rsqldb/tree/main&#xff0c;是和目前stream sql化看齐的Rocketmq的sql&#xff0c;类似还有kafka的sqlDB 和flink sql。 目前版本0.2 &#xff0c;主要提供rest模式调用&#xff0c;controller类为public class RsqlController支持的…

SQL server 文件占用硬盘过大 日志 读写分离同步文件过大清理 DBCC收缩数据库 分发数据库distribution收缩

一顿操作猛如虎 又省出好几十G硬盘空间 小破站又能蹦跶了 目标&#xff1a;实例库日志压缩清理,分发数据库压缩清理 采用SQL 脚本收缩数据库 截断事务日志 backup log [数据库名] with no_log收缩数据库 dbcc shrinkdatabase ([数据库名]) 4.以上操作都不行的话&#xff0…

联发科CEO:未获准向华为供货,换机潮已过去,手机需求不会更差

据钜亨网报道&#xff0c;联发科近期召开了业绩说明会。蔡力行&#xff0c;该公司副董事长兼首席执行官&#xff0c;表明当前手机市场需求保持稳定&#xff0c;并且随着过去两年用户更换潮的过去&#xff0c;对手机市场明年有一定期望。 根据蔡力行的指示&#xff0c;联发科正在…

计算机和医学的交叉融合到底有多强呢?

目录 简介 人工智能在医学诊断中的应用 计算机辅助药物研发 计算机技术在基因组学研究中的应用 数字病理学 穿戴式医疗设备 虚拟现实&#xff08;VR&#xff09;和增强现实&#xff08;AR&#xff09;技术在医学教育中的应用 机器人手术 区块链技术在医学领域的应用 遥…

论文解读:DeepSort(目标跟踪)

本文来自公众号“AI大道理” —————— ​ 论文原文&#xff1a; https://arxiv.org/abs/1703.07402 SORT是一个比较简单的算法&#xff0c;用FrRCNN做探测&#xff0c;卡尔曼滤波和匈牙利算法做跟踪。 缺点&#xff1a; 线性恒速运动模型可能并不精确&#xff0c;未考虑…

二十二章:通过响应缩放进行不确定性估计,以减轻弱监督语义分割中伪掩码噪声的影响

0.摘要 弱监督语义分割&#xff08;WSSS&#xff09;在不需要密集注释的情况下对对象进行分割。然而&#xff0c;生成的伪掩码存在明显的噪声像素&#xff0c;这导致在这些伪掩码上训练的分割模型表现不佳。但是&#xff0c;很少有研究注意到或解决这个问题&#xff0c;即使在改…

【计算机组成原理】页表结构(虚拟内存的映射)

页表结构 引言简单页表多级页表总结 引言 我们的指令和数据&#xff0c;都必须先加载到内存&#xff0c;才会被CPU拿去执行。但是程序并不能直接访问到物理内存。从这里可以知道&#xff0c;程序是怎么装载到内存中执行的。 我们的内存需要被分成固定大小的页&#xff08;Pag…

docker部署Nacos2获取动态配置的失败的坑

Nacos2获取动态配置的失败的坑在此记录 nacos&#xff1a;2.0 依赖也引入了&#xff0c;配置也正确配置了&#xff0c;该写的注解也写了但是报错 [Nacos Config] config[dataIdxxx.yml, groupDEFAULT_GROUP] is empty 原因&#xff1a; nacos官网解释 给nacos容器增加额外两个…