Leetcode 4.18

Leetcode

  • 1.无重复字符的最长子串
  • 2.最长回文子串
  • 3.整数反转
  • 4.字符串转换整数 (atoi)
  • 5.正则表达式匹配

1.无重复字符的最长子串

无重复字符的最长子串
滑动窗口,先让右指针右移,如果发现这个子串有元素和右指针当前元素重复。
则:

  1. 左指针右移,直到移除重复元素为止。
  2. 怎么计算是否有重复?用unordered_map维护子串个数,删除的话数量响应减少,如果count == 0 则将元素erase
  3. 随时更新ans长度,用mp.size()可以轻松算出长度
class Solution {
public:
    int lengthOfLongestSubstring(string s) {
        int ans = 0;
        if (s.size() <= 1) return s.size();
        int l = 0, r = 0;
        unordered_map<char, int> mp;
        while (l <= r && r < s.size()) {
            //当有重复元素时,移动左指针,直到删除了左侧重复元素
            while (mp.count(s[r]) != 0) {
                //重复元素左侧元素都得依次删除
                mp[s[l]]--;
                if (mp[s[l]] == 0) mp.erase(s[l]);
                l++;
            }

            //添加右侧元素,此时已经不重复了
            mp[s[r]]++;
            ans = max(ans, (int)mp.size());  
            r++;
        }
        return ans;
    }
};

2.最长回文子串

最长回文子串
两个要点:

  1. 判断是否为回文串 —> 分奇偶数,l,r指针分别指向头尾,观察r–,l++是否相等
  2. 是否为最长—> 可以用ans维护最长的个数

暴力解法:可以双重循环,依次判断是否为回文串。

class Solution {
public:
    string longestPalindrome(string s) {
        int n = s.size();
        string ans = s.substr(0, 1);
        if (n <= 1) return s;
        for (int i = 0; i < n; i++) {
            for (int j = i; j < n; j++) {
                if (j - i + 1 > ans.size() && ispalindorme(s, i ,j)) {
                    ans = s.substr(i, j - i + 1);
                }
            }
        }
        return ans;
    }
    bool ispalindorme(string s, int l, int r) {
        while (r >= l) {
            if (s[l] != s[r]) {
                return false;
            }
            l++, r--;
        }
        return true;
    }
};

中心扩散法:
给定一个字符串,从中间到两边扩散,判断从左到右范围内最长的回文子串长度。
考虑到奇偶数的不同情况,需要调用两次中心扩散函数。

class Solution {
public:
    string res;
    string longestPalindrome(string s) {
        int n = s.size();
        if (n <= 1) return s;
        for (int i = 0; i < n; i++) {
            extandformmid(s, i, i);
            extandformmid(s, i, i+1);
        }
        return res;
    }

    void extandformmid(string& str, int left, int right) {
        while (left >= 0 && right < str.size() && str[left] == str[right]) {
            left--;
            right++;
        }
        if (right - left - 1 > res.size()) {
            res = str.substr(left + 1, right - left - 1);
        }
    }
};

3.整数反转

整数反转
用ans保存反转后的答案。
在处理数字的过程中判断ans是否有溢出情况发生。
在这里插入图片描述
在这里插入图片描述

class Solution {
public:
    int reverse(int x) {
        int ans = 0;
        while (x) {
            if (ans < INT_MIN / 10 || ans > INT_MAX / 10) {
                return 0;
            }
            ans = ans * 10 + (x % 10);
            x= x / 10;
        }
        return ans;
    }
};

4.字符串转换整数 (atoi)

字符串转换整数 (atoi)
去除前导空格—> while删除
检查正负号—> 有则按照符号,无则为正
读入字符—> ans = ans * 10 + digt
整数范围—>如果下一次ans * 10会溢出,则直接返回这次的结果

class Solution {
public:
    int myAtoi(string s) {
        int ans = 0; int flag = 1;
        int index = 0, n = s.size();
        //删除空格
        while (index < n && s[index] == ' ') index++;
        //检查符号
        if (index < n) {
            if (s[index] == '-') {
                flag = -1;
                index++;
            } else if (s[index] == '+'){
                flag = 1;
                index++;
            }
        }
        //读入字符
        while (index < n && isdigit(s[index])) {
            int dig = s[index] - '0';
            //注意这里严格按照推理所得的公式计算
            if (ans > (INT_MAX - dig) / 10) {
                return flag == 1 ? INT_MAX : INT_MIN;
            }
            ans = ans * 10 + dig;
            index++;
        }
        return ans * flag;
    }
};

5.正则表达式匹配

正则表达式匹配
子串匹配的题目,不由自主的先想DP。

DP分两步:
定义状态
定义状态转移方程

  • 状态
    dp[i][j]表示s[…i]与p[…j]是否能够匹配。dp[s.size()-1][p.size()-1]即为本题答案。

  • 状态转移

    • p[j - 1] = '*' 时, dp[i][j] 在当以下任一情况为 true 时等于 true:

      • dp[i][j - 2]: 即将字符组合 p[j - 2] * 看作出现 0 次时,能否匹配。
      • dp[i - 1][j]s[i - 1] = p[j - 2]: 即让字符 p[j - 2] 多出现 1 次时,能否匹配。
      • dp[i - 1][j]p[j - 2] = '.': 即让字符 '.' 多出现 1 次时,能否匹配。
    • p[j - 1] != '*' 时, dp[i][j] 在当以下任一情况为 true 时等于 true

      • dp[i - 1][j - 1]s[i - 1] = p[j - 1]: 即让字符 p[j - 1] 多出现一次时,能否匹配。
      • dp[i - 1][j - 1]p[j - 1] = '.': 即将字符 . 看作字符 s[i - 1] 时,能否匹配。

p[j-1] == '*'的情况下
1. dp[i][j-2] == True # * 匹配0次,然后s不变,让p[(j-1)-1]匹配0次,相当于消除了一个字符,这里之所以用 [j-2] 是因为相当于 *号和它前面的个字符被丢掉了
2. p[j-2] == s[i-1] and dp[i-1][j] == True # * 匹配多次,这里的多次是可以让前面的1次累加起来的,所以相当于让 * 匹配1次,这里之所以是dp[i-1][j]是因为匹配了一次s中的最后一个字符,所以可以相当于丢掉s中的字符,但是p中的 *和它前面的字符并没有被消耗掉,因为*号可以匹配任意次
3. p[j-2] == '.' and dp[i-1][j] == True # 这里要注意 这里表示*号前面是个'.''.'可以匹配任意字符,所以'.*'可以表示成 … 是上面2中的 p[j-2] == s[i-1] 一种特例
在这里插入图片描述
在这里插入图片描述

class Solution {
public:
    bool isMatch(string s, string p) {
        int n = s.size() + 1, m = p.size() + 1;
        vector<vector<bool>> dp(n, vector<bool> (m, false));
        int i = 1, j = 1;
        //空字符串可以匹配
        dp[0][0] = true;

        // 初始化首行
        for(int j = 2; j < m; j += 2)
            dp[0][j] = dp[0][j - 2] && p[j - 1] == '*';


        for(int i = 1; i < n; i++) {
            for (int j = 1; j < m; j++) {
                if (p[j - 1] == '*') {
                    if (dp[i - 1][j] && s[i - 1] == p[j - 2]) {
                        dp[i][j] = true;
                    //上上个元素为. , 让.多出现几次
                    } else if (dp[i - 1][j] && p[j - 2] == '.') {
                        dp[i][j] = true;
                    //j - 2,指上一个元素为0
                    } else if (dp[i][j - 2]) {
                        dp[i][j] = true;
                    }
                } else {
                    //匹配上了
                    if (dp[i - 1][j - 1] && s[i - 1] == p[j - 1]) {
                        dp[i][j] = true;
                    //是'.'
                    } else if (dp[i - 1][j - 1] && p[j - 1] == '.') {
                        dp[i][j] = true;
                    }
                }
            }
        }
        //
        return dp[n - 1][m - 1];
    }
};

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

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

相关文章

HackmyVM-----Boxing靶机

文章目录 正常打靶流程1.获取靶机IP地址2.获取靶机端口服务3.访问网页4.添加域名WindowsLinux 5.访问域名6.nc反弹shell 7.结束 正常打靶流程 1.获取靶机IP地址 ┌──(root㉿kali)-[/home/kali] └─# arp-scan -l Interface: eth0, type: EN10MB, MAC: 00:0c:29:10:3c:9b, …

Stable Diffusion XL优化终极指南

如何在自己的显卡上获得SDXL的最佳质量和性能&#xff0c;以及如何选择适当的优化方法和工具&#xff0c;这一让GenAI用户倍感困惑的问题&#xff0c;业内一直没有一份清晰而详尽的评测报告可供参考。直到全栈开发者Flix San出手。 在本文中&#xff0c;Flix介绍了相关SDXL优化…

H264标准协议基础3

参考博文 上一篇H264标准协议基础2 1.解码视频帧的poc计算 2.残差4x4 矩阵中的trailingones & numcoeff 2.1查表 trailingones 表达出尾部one(1,-1)系数的个数,按照zigzag扫描出(1,-1)个数,trailingones的最大为3; numcoeff 表达非零值系数的个数,最多为16个…

uniapp开发 如何获取IP地址?

一定要看到最后&#xff01;&#xff01;&#xff01; 一、需求 使用uniapp开发小程序时&#xff0c;需要调取【记录日活动统计】的接口&#xff0c;而这个接口需要传递一个ip给后台&#xff0c; 那么前端如何获取ip呢&#xff1f;下面代码里可以实现 二、代码实现 1.在项…

游戏开发主程进阶之路|主程或高级开发师面试必备之Android和iOS原生APP内嵌CocosCreator引擎

教程地址&#xff1a; 游戏开发主程进阶之路|主程或高级开发师面试必备之Android和iOS原生APP内嵌CocosCreator引擎 Hello大家好&#xff01;&#xff01;相信大家都玩过用过很多类型的APP应用或者游戏APP&#xff1b;现如今很多社交类型的APP或者教育机构的APP会选择通过在应…

demo(四)nacosgateway(2)gatewayspringsercurity

一、思路 1、整体思路 用户通过客户端访问项目时&#xff0c;前端项目会部署在nginx上&#xff0c;加载静态文件时直接从nginx上返回即可。当用户在客户端操作时&#xff0c;需要调用后端的一些服务接口。这些接口会通过Gateway网关&#xff0c;网关进行一定的处理&#xff0…

多线程学习记录

进程是一个个应用程序&#xff0c;线程则可以理解为一个应用进程中的多个功能。有了多线程&#xff0c;便可以让程序同时去做多件事情。 并发:在同一时刻&#xff0c;有多个指令在单个CPU上交替执行 并行:在同一时刻&#xff0c;有多个指令在多个CPU上同时执行 多线程实现 在J…

K8s: 关于Kubernetes中的Pod的创建,实现原理,Job调度pod以及pod网络

Pod 概述 Pod 是最小部署的单元&#xff0c;Pod里面是由一个或多个容器组成&#xff0c;也就是一组容器的集合一个pod中的容器是共享网络命名空间&#xff0c;每个Pod包含一个或多个紧密相关的用户业务容器Pod 是 k8s 系统中可以创建和管理的最小单元是资源对象模型中由用户创…

winform入门篇 第14章 列表控件

列表控件 列表控件 ListView相当于 ListBox的增强版&#xff0c;支持多列显示 最典型的例子:Windows的文件管理器的列表显示 列表控件的几种视图: Detail:详情模式 List: 列表模式 LargeIcon:大图标模式 Smallcon:小图标模式 列表控件的几个特点: 显示模式可以切换 可以…

java高校办公室行政事务管理系统设计与实现(springboot+mysql源码+文档)

风定落花生&#xff0c;歌声逐流水&#xff0c;大家好我是风歌&#xff0c;混迹在java圈的辛苦码农。今天要和大家聊的是一款基于springboot的闲一品交易平台。项目源码以及部署相关请联系风歌&#xff0c;文末附上联系信息 。 项目简介&#xff1a; 基于mvc的高校办公室行政…

excel导出并合并

普通导出数据 需求 需要将相同列数据合并 效果图&#xff1a; 代码&#xff1a; package cn.silence.test;import lombok.AllArgsConstructor; import lombok.Data;/*** 班级信息*/ Data AllArgsConstructor public class ClassInfo {/*** 学院*/private String academy;/**…

OpenHarmony多媒体-ijkplayer

简介 ijkplayer是OpenHarmony环境下可用的一款基于FFmpeg的视频播放器。 演示 编译运行 1、通过IDE工具下载依赖SDK&#xff0c;Tools->SDK Manager->OpenHarmony SDK 把native选项勾上下载&#xff0c;API版本>9 2、开发板选择RK3568&#xff0c;ROM下载地址. 选择…

直流无刷散热风扇的知识原理与内部构成

①直流无刷风扇的结构&#xff1a;主要可分为转子、定子、外框、电机(马达)这四个主要部分以及一些其它的零碎的部件 第一&#xff0c;风扇转子部分: 包括风扇扇叶&#xff0c;是产生空气流动的核心、散热风扇的轴心&#xff0c;用来支撑平衡扇叶滚动、转子磁环&#xff0c;永…

Python路面车道线识别偏离预警

程序示例精选 Python路面车道线识别偏离预警 如需安装运行环境或远程调试&#xff0c;见文章底部个人QQ名片&#xff0c;由专业技术人员远程协助&#xff01; 前言 这篇博客针对《Python路面车道线识别偏离预警》编写代码&#xff0c;代码整洁&#xff0c;规则&#xff0c;易…

Spring Boot + 事务钩子函数,打造高效支付系统!

今天&#xff0c;我继续安利一个独门绝技&#xff1a;Spring 事务的钩子函数。 单纯的讲技术可能比较枯燥乏味。 接下来&#xff0c;我将以一个实际的案例来描述Spring事务钩子函数的正确使用姿势。 一、案例背景 拿支付系统相关的业务来举例。在支付系统中&#xff0c;我们…

Nodejs 第六十四章(SSO单点登录)

单点登录 单点登录&#xff08;Single Sign-On&#xff0c;简称SSO&#xff09;是一种身份认证和访问控制的机制&#xff0c;允许用户使用一组凭据&#xff08;如用户名和密码&#xff09;登录到多个应用程序或系统&#xff0c;而无需为每个应用程序单独提供凭据 SSO的主要优…

openGauss学习笔记-266 openGauss性能调优-TPCC性能调优测试指导-文件系统配置

文章目录 openGauss学习笔记-266 openGauss性能调优-TPCC性能调优测试指导-文件系统配置266.1 查看当前数据盘的文件系统类型266.2 对于需要修改的磁盘&#xff0c;备份所需的数据至其他磁盘或其他服务器266.3 格式化磁盘为xfs文件系统266.4 执行**步骤一** openGauss学习笔记-…

【Keil MDK5新建工程】STM32F103C8T6

一、参数及片上外设 二、系统结构及引脚定义 三、工程架构及新建工程步骤 四、GPIO模式 一、参数及片上外设 二、系统结构及引脚定义 三、工程架构及新建工程步骤 建立工程文件夹&#xff0c;Keil中新建工程&#xff0c;选择型号 工程文件夹里建立Core、Library、User等文件夹…

2024年华中杯数学建模竞赛ABC题思路分析

简单分析一下各个题目可能需要用到的方法和模型&#xff0c;完整代码和成品论文见文末 A题 太阳能路灯光伏板的朝向设计问题: 1. 球面几何、天文学相关知识,如赤纬角、太阳高度角、时角等概念和公式 2. 太阳辐射模型,根据太阳能辐射强度、大气衰减系数等计算地表太阳辐射强度…

绝对隔离+底层限制,成就猎鹰蜜罐“牢不可破”的立体化安全

前言 自网络诞生以来&#xff0c;攻击威胁事件层出不穷&#xff0c;网络攻防对抗已成为信息时代背景下的无硝烟战争。然而&#xff0c;传统的网络防御技术如防火墙、入侵检测技术等都是一种敌暗我明的被动防御&#xff0c;难以有效应对攻击者随时随地发起的无处不在的攻击和威胁…