LeetCode热题HOT100:76. 最小覆盖子串,84.柱状图中最大的矩形、96. 不同的二叉搜索树

news2025/2/28 20:18:17

LeetCode 热题 HOT 100

76. 最小覆盖子串

题目:给你一个字符串 s 、一个字符串 t 。返回 s 中涵盖 t 所有字符的最小子串。如果 s 中不存在涵盖 t 所有字符的子串,则返回空字符串 “” 。
注意:
对于 t 中重复字符,我们寻找的子字符串中该字符数量必须不少于 t 中该字符数量。
如果 s 中存在这样的子串,我们保证它是唯一的答案。
示例 1:
输入:s = “ADOBECODEBANC”, t = “ABC”
输出:“BANC”

package ricky.com.Hot100;

/**
 * @Author xdg
 */
public class minWindow {
    /*
     * 76. 最小覆盖子串
     * 给你一个字符串 s 、一个字符串 t 。返回 s 中涵盖 t 所有字符的最小子串。如果 s 中不存在涵盖 t 所有字符的子串,则返回空字符串 "" 。
     * 注意:
     * 对于 t 中重复字符,我们寻找的子字符串中该字符数量必须不少于 t 中该字符数量。
     * 如果 s 中存在这样的子串,我们保证它是唯一的答案。
     */
    class Solution {
        public String minWindow(String s, String t) {
            if (t == null || t.length() == 0) {
                return "";
            }

            //把t中的每个字符出现的次数统计出来
            int[] arr = new int[128];
            for (int i = 0; i < t.length(); i++) {
                arr[t.charAt(i)]++;
            }

            int l = 0;
            int r = 0;
            //记录t中所有字符出现的次数,为0时说明找到一个答案
            int total = t.length();
            int len = Integer.MAX_VALUE;
            //字符串的起始位置
            int start = 0;
            for (r = 0; r < s.length(); r++) {
                //此时s.charAt(r)字符在t串中,total--
                if (arr[s.charAt(r)] > 0) {
                    total--;
                }
                //arr中t串中对应的字符数量也要减一,但它始终是>=0的,如果字符不在t串中,会减成负数
                arr[s.charAt(r)]--;

                //找到答案,记录
                while (total == 0) {
                    //因为是最小子串,所以取小值
                    if (len > r - l + 1) {
                        //字符串的长度
                        len = r - l + 1;
                        //记录起始位置
                        start = l;
                    }

                    //在将字符移出窗口之前,先要加1,不然移出后就晚了
                    arr[s.charAt(l)]++;
                    if (arr[s.charAt(l)] > 0) {
                        total++;
                    }
                    //窗口右移一位
                    l++;
                }

            }

            return len == Integer.MAX_VALUE ? "" : s.substring(start, start + len);

        }
    }
}

代码解释:

if (t == null || t.length() == 0) {
    return "";
}

如果 t 为空或长度为0,则直接返回空字符串。

int[] arr = new int[128];
for (int i = 0; i < t.length(); i++) {
    arr[t.charAt(i)]++;
}

定义一个长度为128的整型数组 arr,用于统计字符串 t 中每个字符出现的次数。遍历字符串 t,将 arr 中对应字符的计数加1。

int l = 0;
int r = 0;
int total = t.length();
int len = Integer.MAX_VALUE;
int start = 0;

定义五个变量,分别是左指针 l、右指针 r、字符串 t 的长度 total、最小子串长度 len 和最小子串的起始位置 start

for (r = 0; r < s.length(); r++) {
    if (arr[s.charAt(r)] > 0) {
        total--;
    }
    arr[s.charAt(r)]--;
    while (total == 0){
        if (len > r - l + 1){
            len = r - l + 1;
            start = l;
        }
        arr[s.charAt(l)]++;
        if (arr[s.charAt(l)] > 0){
            total++;
        }
        l++;
    }
}

遍历字符串 s,用滑动窗口的方法查找最小子串。当右指针 r 指向的字符在 t 中出现时,将 total 减1;同时将数组 arr 中对应字符的计数减1。当 total 等于0时,表示当前窗口包含了 t 中的所有字符,需要将左指针 l 向右移动,缩小窗口范围。每次移动左指针 l 时,需要将数组 arr 中对应字符的计数加1,如果加1后该字符的计数大于0,则将 total 加1。此外,还需要更新最小子串的长度和起始位置。

return len == Integer.MAX_VALUE ? "" : s.substring(start, start + len);

返回最小子串,如果 len 的值没有被更新过,即没有找到符合要求的子串,则返回空字符串。

84. 柱状图中最大的矩形

题目:给定 n 个非负整数,用来表示柱状图中各个柱子的高度。每个柱子彼此相邻,且宽度为 1 。
求在该柱状图中,能够勾勒出来的矩形的最大面积。
**示例 1:
在这里插入图片描述

输入:heights = [2,1,5,6,2,3]
输出:10
解释:最大的矩形为图中红色区域,面积为 10

package ricky.com.Hot100;

/**
 * @Author xdg
 */
public class largestRectangleArea {
    /*84. 柱状图中最大的矩形
    给定 n 个非负整数,用来表示柱状图中各个柱子的高度。每个柱子彼此相邻,且宽度为 1 。
    求在该柱状图中,能够勾勒出来的矩形的最大面积。*/
    class Solution {
        public int largestRectangleArea(int[] heights) {
            // 定义两个数组,分别用来存储当前柱子左边第一个小于其高度的柱子的下标和右边第一个小于其高度的柱子的下标
            int[] leftMin = new int[heights.length];
            int[] rightMin = new int[heights.length];
            // 初始化左边第一个小于其高度的柱子的下标,第一个柱子左边没有小于其高度的柱子
            leftMin[0] = -1;
            // 初始化右边第一个小于其高度的柱子的下标,最后一个柱子右边没有小于其高度的柱子
            rightMin[heights.length - 1] = heights.length;

            // 遍历所有柱子,计算左边第一个小于其高度的柱子的下标
            for (int i = 1; i < heights.length; i++) {
                int temp = i - 1;
                // 如果当前柱子的高度大于等于左边某个柱子的高度,则将左边柱子的左边第一个小于其高度的柱子的下标作为当前柱子的左边第一个小于其高度的柱子的下标
                while (temp >= 0 && heights[temp] >= heights[i]) {
                    temp = leftMin[temp];
                }
                leftMin[i] = temp;
            }

            // 遍历所有柱子,计算右边第一个小于其高度的柱子的下标
            for (int i = heights.length - 2; i >= 0; i--) {
                int temp = i + 1;
                // 如果当前柱子的高度大于等于右边某个柱子的高度,则将右边柱子的右边第一个小于其高度的柱子的下标作为当前柱子的右边第一个小于其高度的柱子的下标
                while (temp < heights.length && heights[temp] >= heights[i]) {
                    temp = rightMin[temp];
                }
                rightMin[i] = temp;
            }

            // 遍历所有柱子,计算能够勾勒出来的矩形的最大面积
            int res = 0;
            for (int i = 0; i < heights.length; i++) {
                // 当前柱子的高度乘以左边第一个小于其高度的柱子和右边第一个小于其高度的柱子之间的距离就是当前能够勾勒出来的矩形的面积
                res = Math.max(res, heights[i] * (rightMin[i] - leftMin[i] - 1));
            }

            // 返回最大面积
            return res;
        }
    }
}

96. 不同的二叉搜索树

题目:给你一个整数 n ,求恰由 n 个节点组成且节点值从 1 到 n 互不相同的 二叉搜索树 有多少种?
返回满足题意的二叉搜索树的种数。
**示例 1:在这里插入图片描述

输入:n = 3
输出:5

思路分析: 使用一个一维数组 dp 来记录每个节点数能够构成的二叉搜索树的个数。在遍历每个节点数的过程中,枚举左子树节点数 j 和右子树节点数 i-1-j,然后将左右子树能够构成的所有情况之和累加到 dp[i] 中,最终返回 dp[n] 即可。

package ricky.com.Hot100;

/**
 * @Author xdg
 */
class Solution {
    public int numTrees(int n) {
        // 如果输入 n 为 0,返回 0
        if (n == 0) {
            return 0;
        }

        // 定义数组 dp,dp[i] 表示 i 个节点能够构成的二叉搜索树的个数
        int[] dp = new int[n + 1];

        // 初始化 dp[0] 为 1,表示空树也算一种二叉搜索树
        dp[0] = 1;

        // 遍历每个节点数量,从 1 到 n
        for (int i = 1; i <= n; i++) {
            // 遍历左子树节点数量 j,从 0 到 i-1
            for (int j = 0; j < i; j++) {
                // dp[j] 表示左子树能够构成的二叉搜索树的个数
                // dp[i - 1 - j] 表示右子树能够构成的二叉搜索树的个数
                // 二者相乘即为以 j 为根节点,左子树有 dp[j] 种情况,右子树有 dp[i - 1 - j] 种情况的所有情况之和
                dp[i] += dp[j] * dp[i - 1 - j];
            }
        }

        // 返回 dp[n],即 n 个节点能够构成的二叉搜索树的个数
        return dp[n];
    }
}

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

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

相关文章

Ubuntu18.04获取root权限并用root用户登录

写在前面&#xff1a;以下步骤中需要在终端输入命令&#xff0c;电脑端查看博客的朋友可以直接复制粘贴到终端&#xff0c;手机端查看的朋友请注意命令里面的空格是必须的&#xff0c;否则运行会出错。 1.为root设置初始密码 &#xff08;1&#xff09;登录系统&#xff0c;打…

【unity实战】随机地下城生成1

先看看最终效果 导入素材 导入房间图片素材,配置图片信息信息 点击sprite Editor,开始切割图片 随机创建基本房间 已一个白底图片模拟房间预设体 思路:建立一个空的 GameObject 用来做创建房间的点,设置坐标(0,0,0)。每创建1个房间之后,随机在上、下、右判断是否有…

python以及PyCharm工具的环境安装与配置

这里以Windows为例 Python的安装 当然是到Python官网下载咯&#xff0c;https://www.python.org/downloads/点我直达&#xff0c;如图&#xff1a; 可以下载最新版本&#xff0c;可以下拉找到之前特定的版本安装&#xff0c;如图&#xff1a; 这里先择的是最新版的进行安装…

leetcode每日一题:链表专题篇第一期(1/2)

&#x1f61a;一个不甘平凡的普通人&#xff0c;日更算法学习和打卡&#xff0c;期待您的关注和认可&#xff0c;陪您一起学习打卡&#xff01;&#xff01;&#xff01;&#x1f618;&#x1f618;&#x1f618; &#x1f917;专栏&#xff1a;每日算法学习 &#x1f4ac;个人…

现在备考2023年5月软考网络工程师时间够吗?

距离2023年5月软考还有1个多月的时间&#xff0c;备考网络工程师的时间是够的&#xff0c;以下是一些备考方法&#xff1a; 1.了解考试内容 在你开始学习考试之前&#xff0c;了解考试的形式和内容是很重要的。这将帮助你把注意力集中在最有可能被测试的领域。你应该复习考试…

Gartner Magic Quadrant for SD-WAN 2022 (Gartner 魔力象限:软件定义广域网 2022)

Gartner 魔力象限&#xff1a;SD-WAN 2022 请访问原文链接&#xff1a;https://sysin.org/blog/gartner-magic-quadrant-sd-wan-2022/&#xff0c;查看最新版。原创作品&#xff0c;转载请保留出处。 作者主页&#xff1a;sysin.org Gartner 魔力象限&#xff1a;SD-WAN 2022…

ChatGPT最强竞争对手,无需魔法,直接使用

无需科学上网&#xff0c;无需加入Waitlist&#xff0c;免费使用&#xff0c;没有高峰限制&#xff0c;而且效果媲美ChatGPT&#xff01; ChatGPT 的最强竞争对手Claude!!! Claude 是由Anthropic这家人工智能公司开发出来的&#xff0c;其联合创始人Dario Amodei曾经担任OpenAI…

K8S使用持久化卷存储到NFS(NAS盘)

参考文章&#xff1a;K8S-v1.20中使用PVC持久卷 - 知乎 Persistent Volumes&#xff1a;PV是持久化卷&#xff0c;系统管理员设置的存储&#xff0c;它是群集的一部分&#xff0c;是一种资源&#xff0c;所以它有独立于Pod的生命周期 Persistent Volume Claim&#xff1a;PVC…

抽象同步队列AbstractQueuedSynchronizer(AQS)简要理解

抽象同步队列AbstractQueuedSynchronizer AQS 简要理解 1 什么是AQS2 AQS结构2.1 同步状态2.2 CLH队列2.3 Node 3 AQS流程 https://zhuanlan.zhihu.com/p/370501087 1 什么是AQS AQS&#xff08;AbstractQueuedSynchronizer&#xff09;是 Java 中实现锁和同步器的基础设施&am…

el-input-number中添加单位(css版)

优点: 通过css添加,非常便捷和简单 例如此处,需要添加一个分钟单位 <el-input-number class"input-number" v-model"value" :step"5" :min"30" ></el-input-number> //css <style lang"scss"> .input-nu…

node项目(一) koa脚手架的搭建

一、koa 安装 // 安装koa npm install -g koa-generator // 创建项目 koa2 项目名称 当出现这个框的时候安装完毕 之后就是进入目录文件&#xff0c;根据package.json执行即可 二、出现问题 汇总 问题一&#xff1a;koa-generator安装失败 没有出现koa-generator安装成功 …

分类预测 | MATLAB实现BO-CNN-GRU贝叶斯优化卷积门控循环单元多输入分类预测

分类预测 | MATLAB实现BO-CNN-GRU贝叶斯优化卷积门控循环单元多输入分类预测 目录 分类预测 | MATLAB实现BO-CNN-GRU贝叶斯优化卷积门控循环单元多输入分类预测效果一览基本介绍模型描述程序设计参考资料 效果一览 基本介绍 基于贝叶斯(bayes)优化卷积神经网络-门控循环单元(CN…

4月第2周榜单丨飞瓜数据B站UP主排行榜(哔哩哔哩平台)发布!

飞瓜轻数发布2023年4月10日-4月16日飞瓜数据UP主排行榜&#xff08;B站平台&#xff09;&#xff0c;通过充电数、涨粉数、成长指数三个维度来体现UP主账号成长的情况&#xff0c;为用户提供B站号综合价值的数据参考&#xff0c;根据UP主成长情况用户能够快速找到运营能力强的B…

Linux进程概念——其一

目录 冯诺依曼体系结构 操作系统(Operator System) 概念 设计OS的目的 定位 如何理解 "管理" 总结 系统调用和库函数概念 进程 基本概念 描述进程-PCB task_struct-PCB的一种 task_ struct内容分类 组织进程 查看进程 通过系统调用获取进程标示符 通…

Docker Desktop 占用过多C盘存储空间的一种解决办法——在其他磁盘分区添加访问路径

一、问题背景 Docker Desktop默认是安装到C盘中的。但随着Docker的使用&#xff0c;其占用的空间也越来越大&#xff0c;Docker占用C盘空间过大成了个令人头疼的问题。恰好最近腾出了一个空的磁盘分区&#xff0c;因此可以使用“在其他磁盘分区添加访问路径”的方式&#xff0c…

03-Mybatis的基本使用-注解配置文件+xml配置文件

目录 1、环境准备 2、注解配置文件 基础操作01-通过ID删除数据 基础操作02-插入数据 基础操作03-更新数据 基础操作04-根据ID查询数据 基础操作05-条件查询数据 3、xml配置文件 1、环境准备 1. 创建数据库数据表 -- 部门管理 create table dept(id int unsigned prim…

【数据篇】SpringBoot 整合 MyBatis 组合 Redis 作为数据源缓存

写在最前 MyBatis 是常见的 Java 数据库访问层框架。在日常工作中&#xff0c;开发人员多数情况下是使用 MyBatis 的默认缓存配置&#xff0c;但是 MyBatis 缓存机制有一些不足之处&#xff0c;在使用中容易引起脏数据&#xff0c;形成一些潜在的隐患。 本文介绍的是 Redis 组…

版本控制工具之git安装

作为软件开发者的必备工具——版本控制工具&#xff0c;git无疑深受欢迎。 业界常用的版本控制工具主要有两种&#xff1a;SVN和Git SVN 传统的版本控制工具&#xff0c;特点为集中式分布。 使用一台专用的服务器存储所有资料。 缺点是所有的动作都必须依赖于中央服务器&#x…

FPGA配置方式的基本知识?

FPGA配置粗略可以分为主动和被动两种。主动加载是指由FPGA控制配置流程&#xff0c;被动加载是指FPGA仅仅被动接收配置数据。 最常见的被动配置模式就是JTAG下载bit文件。此模式下&#xff0c;主动发起操作的设备是计算机&#xff0c;数据通路是JTAG&#xff0c;FPGA会被动接收…

STM32F103基于HAL库I2C/SPI硬件接口+DMA驱动 SSD1306 Oled

STM32F103基于HAL库I2C/SPI硬件接口DMA驱动 SSD1306 Oled ✨由于手上只有I2C接口的SSD1306 OLED屏幕&#xff0c;仅测试了硬件I2C驱动显示功能&#xff0c;实际测试的FPS帧率在37或38变化。 &#x1f4e2;本项目从Github开源项目中移植过来&#xff0c;开源地址&#xff1a;htt…