数据结构进阶篇,回文字符串专题

2023-11-11


5. 最长回文子串

  「题目」:

  给你一个字符串 s,找到 s 中最长的回文子串。

  「示例」

  输入:s = "babad",输出:"bab"。

  「解题思路」

  首先,判断一个字符串是否为回文字符串,可以采用 双指针 的方式来处理,需要消耗 O(n) 的时间复杂度。

  如果使用首尾向中心扫描的策略,那么就需要 O(n^2) 的时间复杂度来确定子串,而更换为由中心向两边扫描的策略,则只需要 O(n) 的时间复杂度即可确定子串。

  首尾向中心扫描的策略是基于子串确定的前提下,所以不需要考虑字符串的奇偶性。而中心扩展算法只有在识别到首尾字符不一致的情况,才能确定当前子串,而对于奇数长度的字符串和偶数长度的字符串,它们的中心点是不一样的:

  • 奇数长度字符串的中心点:Math.floor(len / 2)。

  • 偶数长度字符串的中心点:len / 2 - 1 和 len / 2。

bd530c10a0e0d92fab6723248dcbd7a2.png

  时间复杂度:O(n^2),空间复杂度:O(1)。

const longestPalindrome = (s) => {
    if (!s) {
        return ''
    }

    let start = 0;
    let end = 0;
    for (let i = 0; i < s.length; i++) {
        const odd = expandAroundCenter(s, i - 1, i + 1);
        const even = expandAroundCenter(s, i, i + 1);
        const len = Math.max(odd.len, even.len);
        if (len > end - start) {
            if (odd.len === len) {
                start = odd.left;
                end = odd.right;
            } else {
                start = even.left;
                end = even.right;
            }
        }
    }

    return s.substring(start, end + 1);
}

function expandAroundCenter (s, left, right) {
    while (left >= 0 && right < s.length && s[left] === s[right]) {
        --left;
        ++right;
    }

    return {
        left: left + 1,
        right: right - 1,
        len: right - left - 1
    }
}

131. 分割回文串

  「题目」

  给你一个字符串 s,请你将 s 分割成一些子串,使每个子串都是回文串 。返回 s 所有可能的分割方案。

  「示例」

  输入:s = "aab",输出:[["a","a","b"],["aa","b"]]。

  「解题思路」

  由于题目要求返回所有的分割方案,所以只能采用回溯的方式进行枚举。

  由于本道题的第一个回文字符串的起点是固定的,所以只能采用首尾向中心扫描的算法来判断当前子串是否为回文字符串。

  时间复杂度:O(n2^n),空间复杂度:O(2^n)。

const partition = s => {
  const max = s.length
  const ans = []
  const path = []

  backtrack(s, 0, path, ans, max);
  return ans
}

function backtrack(str, position, path, ans, max) {
  if (position === max) {
    return ans.push([...path]);
  }

  for (let i = position; i < max; i++) {
    if (isPalindrome(str, position, i)) {
      path.push(str.substring(position, i + 1))
      backtrack(str, i + 1, path, ans, max);
      path.pop();
    } 
  }
}

function isPalindrome(str, start, end) {
  while (start < end) {
    if (str[start] === str[end]) {
      start++;
      end--;
    } else {
      return false;
    }
  }

  return true;
}

516. 最长回文子序列

  「题目」

  给你一个字符串 s ,找出其中最长的回文子序列,并返回该序列的长度。

  子序列定义为:不改变剩余字符顺序的情况下,删除某些字符或者不删除任何字符形成的一个序列。

  「示例」

  输入:s = "bbbab";输出:4;解释:一个可能的最长回文子序列为 "bbbb" 。

  「解题思路」

  最值问题可以通过动态规划来进行记忆化枚举,用 dp[i][j] 表示字符串下标范围 [i, j] 内最大回文子序列的长度。

  首先对于任意长度为1的子序列来说,其都是回文子序列,即 dp[i][i] = 1。

  当 i < j 时,只需要考虑 s[i] 和 s[j] 是否相等即可:

  • s[i] === s[j]:此时 [i, j] 范围内的子序列为回文子序列,即 dp[i][j] = dp[i + 1][j - 1] + 2。

  • s[i] !== s[j]:此时 s[i] 和 s[j] 不可能同时作为回文子序列的首尾,那么此时 dp[i][j] 最长回文子序列应该存在于 dp[i + 1][j] 或者是 dp[i][j - 1] 中,即 dp[i][j] = Math.max(dp[i + 1][j], dp[i][j - 1])。

  由上述推导过程可以知道,i 应该从后往前遍历,因为需要执行 i + 1 的状态转移;j 应该向后遍历,应为需要执行 j - 1 的状态转移。

  时间复杂度:O(n^2),空间复杂度:O(n^2)。

const longestPalindromeSubseq = function(s) {
    const max = s.length
    const dp = Array(max).fill(0).map(() => Array(max).fill(0))
    for (let i = max - 1; i >= 0; i--) {
        dp[i][i] = 1;
        const c1 = s[i];
        for (let j = i + 1; j < max; j++) {
            const c2 = s[j];
            if (c1 === c2) {
                dp[i][j] = dp[i + 1][j - 1] + 2;
            } else {
                dp[i][j] = Math.max(dp[i + 1][j], dp[i][j - 1]);
            }
        }
    }

    return dp[0][max - 1];
};

647. 回文子串

  「题目」

  给你一个字符串 s ,请你统计并返回这个字符串中 回文子串 的数目。

  「示例」

  输入:s = "abc",输出:3,解释:三个回文子串: "a", "b", "c"。

  「解题思路」

  本道题目可以采用《5. 最长回文子串》的解题思路,并且由于本题只需要求解数目,所以不涉及额外状态的保存,解题代码显得更加清晰。

  时间复杂度:O(n^2),空间复杂度:O(1)。

var countSubstrings = function(s) {
    let ans = 0;
    const max = s.length;

    for (let i = 0; i < max; i++) {
        ans++;
        let start = i - 1;
        let end = i + 1;
        while (start >= 0 && end < max && s[start] === s[end]) {
            ans++;
            start--;
            end++;
        }
    }

    for (let i = 1; i < max; i++) {
        let start = i - 1;
        let end = i;

        while (start >= 0 && end < max && s[start] === s[end]) {
            ans++;
            start--;
            end++;
        }
    }

    return ans;
};

写在最后

  「感谢您能耐心地读到这里,如果本文对您有帮助,欢迎点赞、分享、或者关注下方的公众号哟。」

  相关链接:

  • 最长回文子串 https://leetcode-cn.com/problems/longest-palindromic-substring/

  • 分割回文串 https://leetcode-cn.com/problems/palindrome-partitioning/

  • 最长回文子序列 https://leetcode-cn.com/problems/longest-palindromic-subsequence/

  • 回文子串 https://leetcode-cn.com/problems/palindromic-substrings/

5aa8d99a5b4809fb489872c4ce33d23f.png

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

数据结构进阶篇,回文字符串专题 的相关文章

  • 摆动刷新周期

    我试图了解何时使用重新验证 重绘 打包 令人惊讶的是 我没有找到详细的底层文档 请随意链接 到目前为止我已经明白这都是 RepaintManager 的责任 油漆 重新油漆指的是脏 干净的东西 pack validate revalidat
  • 字母表中的加密和解密 - Python GCSE

    我目前正在尝试为学校编写一个程序 以便加密和解密输入的消息 我需要加密或解密的消息仅在字母表中 没有其他符号或密钥 例如 使用消息车加密输入的偏移量为 5 我希望它输出 afs 有人可以帮忙吗 这是我目前的代码 def find offse
  • 如何在 apache poi 中找到包含图片的单元格

    我尝试在 xls 文档中循环图像 我写下一个代码 HSSFPatriarch patriarch sheet getDrawingPatriarch if patriarch null Loop through the objects fo
  • 如何抑制 pyinstaller 生成的可执行文件窗口中的所有警告

    我已经使用 pyinstaller 从 python 文件生成了可执行文件 该程序按其应有的方式工作 但在我想隐藏的窗口中出现了一条警告消息 当 python 文件在 IDE 中运行时 以下行会抑制所有警告消息 warnings filte
  • Java 通用问题

    下面的代码可以编译 但如果我取消注释行 它不会编译 我很困惑为什么 HashMap 确实扩展了 AbstractMap 并且声明映射的第一行可以正常编译 import java util AbstractMap import java ut
  • 对于 pygtk 应用程序来说,什么是好的嵌入式浏览器?

    我计划在我的 pygtk 应用程序中使用嵌入式浏览器 并且我正在 gtkmozembed 和 pywebkitgtk 之间进行辩论 两者之间有什么引人注目的区别吗 还有我不知道的第三种选择吗 应该注意的是 我不会使用它来访问网络上的内容 我
  • 监控单个文件

    我需要监控 使用watchdog http pythonhosted org watchdog index html 单个文件 而不是整个目录 避免监视整个目录的最佳方法是什么 我想this http pythonhosted org wa
  • Hive NVL 不适用于列的日期类型 - NullpointerException

    我正在使用 HDFS 上的 MapR Hive 发行版并面临以下问题 如果表的列类型是 日期 类型 则NVL https cwiki apache org confluence display Hive LanguageManual UDF
  • 如何替换被测模块的文件访问引用

    pyfakefs https code google com p pyfakefs 听起来非常有用 它 最初是作为核心 Python 模块的一个适度的假实现来开发的 以支持中等复杂的文件系统交互 并于 2006 年 9 月在 Google
  • Python unittest - 与assertRaises相反?

    我想编写一个测试来确定在给定情况下不会引发异常 测试是否有异常很简单is上调 sInvalidPath AlwaysSuppliesAnInvalidPath self assertRaises PathIsNotAValidOne MyO
  • 在 Java Web 应用程序中获取 DataSource 资源

    我的 context xml 文件中有以下资源标记
  • import numpy 和 import numpy as np 之间的区别

    我明白 如果可能的话 应该使用 import numpy as np 这有助于避免由于命名空间引起的任何冲突 但我注意到虽然下面的命令有效 import numpy f2py as myf2py 以下不 import numpy as np
  • 如果可能,将 jFrame 输出到第二台显示器

    我在 Java 中的 Swing 上有一个 jFrame 我希望它输出到第二个监视器 如果该监视器存在 我尝试过这个 通过this http download oracle com javase 6 docs api java awt Gr
  • Tornado websocket handler , self.close() 正在关闭连接而不触发 on_close() 方法

    我是 python stackoverflow tornado 的新手 所以请耐心等待 纠正我 我正在使用龙卷风开发实时应用程序 当我在 Websocket 处理程序类中调用 self close 时 on close 方法不会启动 这次我
  • 从 sublime_plugin.WindowCommand 获取当前文件名

    我开发插件sublime text 3 并想要获取当前打开的文件路径 absolute1 self window view file name 在哪里self is sublime plugin WindowCommand 但失败了 Att
  • 检测图像是否损坏或损坏

    我需要以编程方式检查用户在我的应用程序上选择作为壁纸的图像是否已损坏或损坏 基本上我为用户提供了选择自己的图像作为壁纸的选项 现在 当图像加载时 我只想检查它是否已损坏 如果您正在寻找 PHP 解决方案而不是 javascript 解决方案
  • 在字典理解中为 locals() 添加下标失败并出现 KeyError [重复]

    这个问题在这里已经有答案了 我对 Python 的奇怪行为感到困惑locals 基本上我想从字典中获取一个项目locals 在字典理解中 但它失败了 这是一个非常基本的事情 所以 gt gt gt foo 123 gt gt gt bar
  • 用于桌面数据库应用程序的 Python 框架

    是否有一个框架可以为Python开发桌面数据库应用程序 一些带有CRUD屏幕的屏幕 我正在寻找类似于 Windows 窗体的东西 能够将 TextField Combos 和其他 UI 隐喻与datasets连接到关系数据库例如 MySQL
  • python pandas如何在多个条件下过滤字符串

    我有以下数据框 import pandas as pd data 5Star FiveStar five star fiv estar data pd DataFrame data columns columnName 当我尝试用一 种条件
  • 连接运算符 + 或 ,

    var1 abc var2 xyz print literal var1 var2 literalabcxyz print literal var1 var2 literal abc xyz 除了带有 的自动空格之外 两者有什么区别 哪个通

随机推荐

  • FileZilla的下载与安装

    FileZilla的下载与安装 为什么要使用FileZilla进行文件互传呢 Windows下 FileZilla客户端下载与安装 1 FileZilla的下载 1 FileZilla的安装 1 双击运行安装包 点击 i agree 2 n
  • Shader中的一些专业用语的解释

    Shader中的一些专业用语的解释 此文章收录于我主页顶置的 Unity Shader入门精要文章目录 点击即可跳转 一 什么是OPenGL DirectX 简单的来说 就是图像应用编程的接口 这些接口用语渲染二维和三维的图形 架起了上层应
  • 【毕业设计】基于单片机的桌面炫酷律动灯条 -物联网 嵌入式 单片机

    文章目录 0 前言 1 简介 2 主要器件 3 实现效果 4 设计原理 5 部分核心代码 6 最后 0 前言 这两年开始毕业设计和毕业答辩的要求和难度不断提升 传统的毕设题目缺少创新和亮点 往往达不到毕业答辩的要求 这两年不断有学弟学妹告诉
  • 公办幼儿园教师要涨工资了???

    终于盼到这一天了 已在市区公办园上班3年多却一直没有编制的季馨 听说从明年开始要涨工资了 高兴坏了 记者从日前召开的全市学前教育工作会议上获悉 从2012年起 确保市区公办幼儿园中具有国家教师资格的聘用教师最低工资水平不得低于当地最低工资标
  • 蓝桥杯 问题 1083: Hello, world!(C/C++ vector实现)

    问题 1083 Hello world 时间限制 1Sec 内存限制 64MB 提交 944 解决 476 题目描述 This is the first problem for test Since all we know the ASCI
  • 《一周搞定模电》—功率放大器

    系列文章目录 文章目录 系列文章目录 前言 一 功率放大电路三极管的工作模式 二 功率放大器内部结构 前言 功率放大器指一种以输出较大功率为目的的放大电路 特点 输出电压大 输出电流大 放大电路的输出电阻与负载匹配 电压放大器和功率放大器的
  • 三子棋创作(c语言)

    我们写三子棋之前首先要思考一下三子棋的实现逻辑 一 1 游戏菜单 是选择开始游戏还是结束游戏 2 打印一个棋盘出来 并且进行棋盘的初始化 即没有旗子的棋盘 3 玩家下棋 用 表示 4 电脑下棋 用 表示 5 判断胜负 电脑和玩家下完棋之后
  • java使用lambda表达式对List集合进行操作(Java8)

    import java util ArrayList import java util List import java util function Predicate import java util stream Collectors
  • token会被截取吗_OAuth2 为什么要用 code 换 token

    先简单介绍下 OAuth2 再用一个例子说明下为什么要用 code 换 token OAuth2 简单介绍 4 个角色 resource owner 可以授权访问被保护资源的实体 如果是人的话 即是最终用户 resource server
  • h2数据库优缺点

    h2数据库是嵌入式的内存型数据库 也可以存储在磁盘上 效率比通过socket调用的redis执行的要快 纯java编写就一个jar h2数据库的缺点是不适合大数据量高并发的操作
  • centos 安装防火墙,并开启对应端口号

    1 查看防火墙状态 命令 systemctl status firewalld service 开启防火墙时 提示没有安装防火墙 root localhost systemctl start firewalld service Failed
  • 关于锁的面试题

    1 synchronized和ReentranctLock有什么区别 底层实现 synchronized是jvm层面的锁 通过monitor对象完成 对象只能在同步代码块和同步方法中调用wait notify方法 ReentranctLoc
  • Java多线程——线程的sleep方法、中断线程的睡眠

    一 关于Sleep方法的应用 public static void sleep long millis throws InterruptedException 让当前正在执行的线程进入休眠 暂时停止执行 指定的毫秒数 静态方法 Thread
  • 数字媒体技术专业方向

    现在是大三下 这篇文章是大一时 整理知乎青岛大学 某学姐的高赞回答 咱这个专业 你可以根据你的学校进行选择 学校好 按部就班的学 以下几个方向都走得通 学校不好 很普通 那么大概率也不学了什么 普通本科院校的学风啊 教学质量啊 与其都学个皮
  • C++11/14/17中提供的mutex系列区别

    C 11 14 17中提供的mutex系列类型如下 互斥量 C 版本 作用 mutex C 11 基本的互斥量 timed mutex C 11 timed mutex带超时功能 在规定的等待时间内 没有获取锁 线程不会一直阻塞 代码会继续
  • 监听小程序切换到后台

    注意要写在app js里面 onHide wx onAppHide
  • 图像处理学习笔记(三):基于匹配的目标识别

    Matlab图像处理学习笔记 三 基于匹配的目标识别 如果要在一幅图像中寻找已知物体 最常用且最简单的方法之一就是匹配 在目标识别的方法中 匹配属于基于决策理论方法的识别 匹配方法可以是最小距离分类器 相关匹配 本文code是基于最小距离分
  • 三进制计算机_数学糖果S10:N进制

    不同进制各有各的特点 二进制更为基础 十进制匹配人体手指数量 十二进制之基数12所含因数多 十六进制之基数16易被多次二分 六十进制结合了五进制与十二进制 世界可能是由概率控制的 现实世界中十进制被选中 计算机世界中二进制被选中 N 进 制
  • PyTorch: 训练分类CIFAR10

    usr bin env python coding utf 8 Author zengxiaohui Datatime 8 13 2021 11 20 AM File train cifar10 import os import torch
  • 数据结构进阶篇,回文字符串专题

    5 最长回文子串 题目 给你一个字符串 s 找到 s 中最长的回文子串 示例 输入 s babad 输出 bab 解题思路 首先 判断一个字符串是否为回文字符串 可以采用 双指针 的方式来处理 需要消耗 O n 的时间复杂度 如果使用首尾向