LeetCode-hot100题解—Day7

原题链接:力扣热题-HOT100
我把刷题的顺序调整了一下,所以可以根据题号进行参考,题号和力扣上时对应的,那么接下来就开始刷题之旅吧~
1-8题见LeetCode-hot100题解—Day1
9-16题见LeetCode-hot100题解—Day2
17-24题见LeetCode-hot100题解—Day3
25-34题见LeetCode-hot100题解—Day4
39-56题见LeetCode-hot100题解—Day5
62-71题见LeetCode-hot100题解—Day6
注:需要补充的是,如果对于每题的思路不是很理解,可以点击链接查看视频讲解,是我在B站发现的一个宝藏UP主,视频讲解很清晰(UP主用的是C++),可以结合视频参考本文的java代码。

力扣hot100题解 62-71

    • 72.编辑距离
    • 75.颜色分类
    • 78.子集

72.编辑距离

思路
本题采用动态规划来解决,设f(i,j)为匹配word1中的前i个字符和word2中的前j个字符所需要的最少步数,f(i,j)的值可分为两种情况
(1)word1[i] == word2[j]:此时不需要进行任何操作即可匹配,f(i,j) = f(i-1,j-1)
(2)word1[i] != word2[j]:由于有三种操作可供选择,所以又分为三种情况,最后的结果需要在这三种情况中取最小值:

  • 插入:在word1[i]的后面插入word2[j],回到第一种情况,此时word1[i+1]
    =word2[j],所以f(i,j)=f(i,j-1)+1(这个+1是指插入操作)
  • 删除:删除word1[i],此时需要比较word1[i-1]word2[j],所以f(i,j)=f(i-1,j)+1(+1是指删除操作)
  • 替换:替换word1[i]word2[j],此时与第一种情况完全相同,f(i,j)=f(i-1,j-1)+1(+1是指替换操作)

需要注意的是,我们需要对第一行和第一列特殊处理,在两个字符串前加上空格,在初始化第一列时,f[i][0]表示word1的前i个字符匹配word2[0]的最少步骤,也就是匹配空字符串的步数,因此替换word1i个字符为空字符即可,所以步骤为i,初始化第一行同理,视频讲解点击视频讲解-编辑距离。
时间复杂度
这段代码的时间复杂度为 O(n * m),其中 nword1 的长度,mword2 的长度。
代码实现

class Solution {
    public int minDistance(String word1, String word2) {
        int n = word1.length();
        int m = word2.length();
        //给word1和word2前面添加空格,方便处理,所以在后面f数组时,长度要+1
        word1 = ' ' + word1;
        word2 = ' ' + word2;
        //创建二维数组并初始化
        int[][] f = new int[n + 1][m + 1];
        for(int[] item : f){
            Arrays.fill(item,Integer.MAX_VALUE);
        }

        //处理第一行和第一列
        for(int i = 0; i <= n;i++) f[i][0] = i;
        for(int j = 0; j <= m;j++) f[0][j] = j;

        for(int i = 1;i <= n;i++){
            for(int j = 1;j <= m;j++){
                if(word1.charAt(i) == word2.charAt(j)){
                    f[i][j] = f[i - 1][j - 1];
                }else{
                    f[i][j] = Math.min(f[i - 1][j - 1],Math.min(f[i - 1][j],f[i][j - 1])) + 1;
                }
            }
        }
    return f[n][m];
    }
}

75.颜色分类

思路
本题采用三指针解决,使用三个指针ijk来分别表示红色、白色、蓝色的分界位置,通过while循环遍历数组,当j指向的元素为0时,与i位置的元素进行交换,同时将ij都向后移动一位。当j指向的元素为2时,与k位置的元素进行交换,同时将k向前移动一位。如果j指向的元素为1,则仅将j向后移动一位。这样遍历一次数组后,就可以将数组中的0全部移动到前面,将2全部移动到后面,1的位置则自然被安排在中间。
这里说明一下为什么j指向0时交换后需要后移而指向2时交换不用后移,原因在于ij是同时从索引0处出发的,在j指向的值为2时,与k指向的值交换,此时k之前指向的值是多少我们是不知道的,可能交换后j指向的新值还需要进行交换,所以此时j指针是不用动的,k指针后移;i指针和j指针刚开始是同步的(指向0和2的时候ij要么都移动,要么都不移动),只有在指向1的时候j指针后移,i指针不动,所以可以得出j指针和i指针要么同步,要么j指针会在i指针的后面,所以i指针不会指向2(除了索引0处的值是2的情况下),只会指向0和1,且i指针前面的数全部都是0,如果还是不太理解这一点,可以自己多模拟几个例子,视频讲解点击视频讲解-颜色分类。
时间复杂度
时间复杂度为O(n),其中n为数组nums的长度。
代码实现

class Solution {
    public void sortColors(int[] nums) {
        int i = 0;
        int j = 0;
        int k =nums.length - 1;
        while(j <= k){
            if(nums[j] == 0){
                swapnum(nums,i,j);
                i++;
                j++;
            }
            else if(nums[j] == 2) {
                swapnum(nums,j,k);
                k--;
            }
            else j++;
        }
    }
    //注意:这里不能简单的交换两个数(即swap(int a,int b)),因为交换的只是形参的值,并不会影响到原始数组nums中的值
    //所以应该修改为交换数组中指定位置的值,而不是交换形参的值
    private void swapnum(int[] nums,int i,int j){
        int temp = nums[i];
        nums[i] = nums[j];
        nums[j] = temp;
    }
}

78.子集

思路一深度优先搜索
本题正常解法是采用深度优先遍历来解决,枚举的方法是看每个位置的元素是否选择,当枚举到最后一个元素后,将结果添加到结果集中,注意回溯之后也要进行深度优先搜索,这样才能返回子集的全集。
时间复杂度
这个算法的时间复杂度是O(2^N),其中Nnums数组的长度。在每一层递归中,我们有两种选择:选择当前元素和不选择当前元素。因此,递归树的高度是N,每个节点有两个分支。总共有2^N个节点。所以时间复杂度是O(2^N)
代码实现

class Solution {
    List<List<Integer>> ans = new ArrayList<>();
    List<Integer> subset = new ArrayList<>();
    public List<List<Integer>> subsets(int[] nums) {
      dfs(nums,0);
      return ans;  
    }

    private void dfs(int[] nums,int idx){
        if(idx == nums.length){
            ans.add(new ArrayList<>(subset));
            return;
        }
        //添加当前元素并深度优先搜索
        subset.add(nums[idx]);
        dfs(nums,idx + 1);
        //丢弃当前元素并深度优先搜索,回溯
        subset.remove(subset.size() - 1);
        dfs(nums,idx + 1);
    }
}

思路2二进制法
由于数组中无重复元素,那么我们可以用二进制的位数来表示数组中的元素(n个元素即二进制为2^n,它的子集有2^n个),我们知道二进制是0和1的组合,当某一位为1时说明该位置对应的元素被选择了,由于二进制包含所有的组合,所以将0-2^n中所有的二进制数按照上述规则对应成子集,每一个二进制数字对应一个子集(对应位置为0即不选择,对应位置为1即选择),则可以得到子集的全集,视频讲解点击视频讲解-子集,视频中有详细的模拟举例。
时间复杂度
这段代码的时间复杂度为O(2^n * n),其中n为数组nums的长度。这是因为对于nums数组的每个元素,都有可能在子集中存在或不存在,所以一共有2^n种可能的子集组合,并且在每一种可能中,需要花费O(n)的时间来生成子集。因此,整体的时间复杂度为O(2^n * n)
代码实现

class Solution {
    public List<List<Integer>> subsets(int[] nums) {
        List<List<Integer>> ans = new ArrayList<>();
        int n = nums.length;
        for(int mask = 0;mask < (1 << n); mask++){
            List<Integer> subset = new ArrayList<>();
            for(int i = 0; i < n; i++){
                //(mask & (1 << i)) != 0表示索引为i的位置对应的mask二进制为1,所以将nums[i]加进subset
                if((mask & (1 << i)) != 0) subset.add(nums[i]);
            }
            ans.add(new ArrayList<>(subset));
        }
        return ans;
    }
}

综上,还是建议使用我们常用的dfs,简单并且耗时少。
由于力扣更新了,刷题顺序被打乱了,所以我准备调整一下刷题策略,按照知识点刷题,先讲解知识点,然后从hot100里找例题,这样更高效一点,在这里说明一下下~

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

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

stm32_RTC_2_HAL——stm32CudeMX

介绍 RTC&#xff08;实时时钟&#xff09;不仅仅提供计数功能&#xff0c;它是一个完整的时钟和日历模块&#xff0c;用于提供日期和时间信息。RTC 能够提供年、月、日、星期、时、分、秒等时间信息&#xff0c;并且通常具有闹钟功能&#xff0c;可以用于定时唤醒或触发事件。…

Qt | QLineEdit 类(行编辑器)

01、上节回顾 Qt | QComboBox(组合框)02、QLineEdit 1、QLineEdit 类是 QWidget 类的直接子类,该类实现了一个单行的 输入部件,即行编辑器,见右图 2、验证器(QValidator 类)和输入掩码简介:主要作用是验证用户输入的字符是否符合验证器 的要求,即限制对用户的输入,比…

详细介绍ARM-ORACLE Database 19c数据库下载

目录 1. 前言 2. 获取方式 2.1 ORACLE专栏 2.2 ORACLE下载站点 1. 前言 现有网络上已有非常多关于ORACLE数据库机下载的介绍&#xff0c;但对于ARM平台的介绍不多&#xff0c;借此机会我将该版的下载步骤做如下说明&#xff0c;希望能够一些不明之人提供帮助和参考 2. 获…

【STM32G474】利用Cpp编写STM32代码后,Cubemx修改配置后代码报错147个error,如何处理?

问题描述 打开Cubemx&#xff0c;添加TIM7用于定时器精准延时&#xff0c;生成代码后&#xff0c;Keil提示有147个error。 之前是Cubemx是没有问题的&#xff0c;是利用Cpp编写stm32&#xff08;将Keil改为Version6&#xff09;后才导致Cubemx配置失败&#xff1a; debug成功…

[学习笔记]CyberDog小米机器狗 开发学习

1、机器狗本身是UbuntuROS2系统 2、控制机器人只需要了解lcm和Ros topic通讯 3、传感器数据&#xff08;包括一些imu(/imu)、激光雷达(/scan)&#xff09;会进行topic的一个广播。 仿真环境通信接口&#xff1a; -命令输入(见后续运控说明) 运控lcm数据接口 Motion man…

Gmail邮箱怎么注册?2024年完整指南(包含跳过手机号验证)

一、为什么要注册Gmail邮箱&#xff1f; 全球通用性&#xff1a;Gmail是一个全球性的邮件服务平台&#xff0c;被广泛认可和信赖。因为客户对于Gmail的接受度高&#xff0c;无需担心邮件被自动标记为垃圾邮件。 整合营销工具&#xff1a;通过Gmail账号&#xff0c;你可以轻松…

CleanMyMac X 4.15.3 版本发布

CleanMyMac X 4.15.3 版本发布&#xff0c;一款苹果 macOS 系统好用的伴侣软件&#xff0c;其包含 1.一键深度清理。2.系统垃圾专清。3.大/旧文件专清。4.系统提速。5.性能悬浮窗。6.恶意软件防护。7.隐私保护。8.软件卸载器。9.软件更新器等 9 大功能&#xff0c;为您的苹果电…

Flask-HTTP请求、响应、上下文、进阶实验

本节主要目录如下&#xff1a; 一、请求响应循环 二、HTTP请求 2.1、请求报文 2.2、Request对象 2.3、在Flask中处理请求 2.4、请求钩子 三、HTTP响应 3.1、响应报文 3.2、在Flask中生成响应 3.3、响应格式 3.4、Cookie 3.5、session&#xff1a;安全的Cookie 四、…

[公开课学习]台大李宏毅-自注意力机制 Transformer

自注意力机制 存在一些问题&#xff0c;将vector set/sequence作为input&#xff0c;例如&#xff1a; 文字处理&#xff1a;将文字用one-hot表示&#xff0c;或者向量空间的向量表示&#xff0c;然后进行翻译任务等语音处理&#xff1a;25ms音频作为一个向量&#xff0c;10m…

初识C++ · 模板初阶

目录 1 泛型编程 2 函数模板 3 类模板 1 泛型编程 模板是泛型编程的基础&#xff0c;泛型我们碰到过多次了&#xff0c;比如malloc函数返回的就是泛型指针&#xff0c;需要我们强转。 既然是泛型编程&#xff0c;也就是说我们可以通过一个样例来解决类似的问题&#xff0c…

pytorch基础: torch.unbind()

1. torch.unbind 作用 说明&#xff1a;移除指定维后&#xff0c;返回一个元组&#xff0c;包含了沿着指定维切片后的各个切片。 参数&#xff1a; tensor(Tensor) – 输入张量dim(int) – 删除的维度 2. 案例 案例1 x torch.rand(1,80,3,360,360)y x.unbind(dim2)print(&…

gitlab集群高可用架构拆分部署

目录 前言 负载均衡器准备 外部负载均衡器 内部负载均衡器 (可选)Consul服务 Postgresql拆分 1.准备postgresql集群 手动安装postgresql插件 2./etc/gitlab/gitlab.rb配置 3.生效配置文件 Redis拆分 1./etc/gitlab/gitlab.rb配置 2.生效配置文件 Gitaly拆分 1.…

BACnet转MQTT网关智联楼宇json格式自定义

智能建筑的BACnet协议作为楼宇自动化领域的通用语言&#xff0c;正逐步迈向更广阔的物联网世界。随着云计算和大数据技术的飞速发展&#xff0c;如何将BACnet设备无缝融入云端生态系统&#xff0c;成为众多楼宇管理者关注的焦点。本文将以一个实际案例&#xff0c;揭示BACnet网…

60、郑州大学附属肿瘤医院 :用于预测胃癌患者术后生存的深度学习模型的开发和验证[同学,我们的人生应当是旷野]

馒头老师要说的话&#xff1a; 我近期看了一下北京的脑机公司&#xff0c;大概是我之前对这一行业太过于乐观&#xff0c;北京的BCI公司和研究所&#xff0c;比上海、深圳、杭州甚至是重庆都要少&#xff0c;门槛也要高很多。也有我自己的原因&#xff0c;有时站的太高&#x…

92、动态规划-最小路径和

思路&#xff1a; 还是一样&#xff0c;先使用递归来接&#xff0c;无非是向右和向下&#xff0c;然后得到两种方式进行比较&#xff0c;代码如下&#xff1a; public int minPathSum(int[][] grid) {return calculate(grid, 0, 0);}private int calculate(int[][] grid, int …

ubuntu_Docker安装配置

什么是docker? Docker 是一个开源的应用容器引擎&#xff0c;让开发者可以打包他们的应用以及依赖包到一个可移植的镜像中&#xff0c;然后发布到任何流行的 Linux或Windows操作系统的机器上&#xff0c;也可以实现虚拟化。容器是完全使用沙箱机制&#xff0c;相互之间不会有…

为什么要梯度累积

文章目录 梯度累积什么是梯度累积如何理解理解梯度累积梯度累积的工作原理 梯度累积的数学原理梯度累积过程如何实现梯度累积 梯度累积的可视化 梯度累积 什么是梯度累积 随着深度学习模型变得越来越复杂&#xff0c;模型的训练通常需要更多的计算资源&#xff0c;特别是在训…

深度学习笔记_10YOLOv8系列自定义数据集实验

1、mydaya.yaml 配置方法 # 这里分别指向你训练、验证、测试的文件地址&#xff0c;只需要指向图片的文件夹即可。但是要注意图片和labels名称要对应 # 训练集、测试集、验证机文件路径&#xff0c;可以是分类好的TXT文件&#xff0c;也可以直接是图片文件夹路径 train: # t…

Litedram仿真验证(四):AXI接口完成板级DDR3读写测试(FPGA-Artix7)

目录 日常唠嗑一、仿真中遗留的问题二、板级测试三、工程获取及交流 日常唠嗑 接上一篇Litedram仿真验证&#xff08;三&#xff09;&#xff1a;AXI接口完成仿真&#xff08;FPGA/Modelsim&#xff09;之后&#xff0c;本篇对仿真后的工程进行板级验证。 本次板级验证用到的开…

学成在线 - 第3章任务补偿机制实现 + 分块文件清理

7.9 额外实现 7.9.1 任务补偿机制 问题&#xff1a;如果有线程抢占了某个视频的处理任务&#xff0c;如果线程处理过程中挂掉了&#xff0c;该视频的状态将会一直是处理中&#xff0c;其它线程将无法处理&#xff0c;这个问题需要用补偿机制。 单独启动一个任务找到待处理任…
最新文章