当前位置: 首页 > news >正文

力扣 | 动态规划 | 在字符串的应用 | 最长回文子串、最长回文子序列、单词拆分、编辑距离

文章目录

  • 1.最长回文子串
  • 2.最长回文子序列
  • 3.单词拆分
  • 4.编辑距离
  • 5. 共同点和思路
  • 6. 各个问题的思路和扩展
    • 1. 最长回文子串
    • 2. 最长回文子序列
    • 3. 单词拆分
    • 4. 编辑距离

在解答字符串动态规划的应用时,我们需要非常注意一个问题:
  有时候我们定义 d p [ i ] [ j ] dp[i][j] dp[i][j]表示第一个字符串的第i个字符,第二个字符串的第j个字符。 d p [ 0 ] [ 0 ] dp[0][0] dp[0][0]表示两个都为空串时。
  使用数组下标访问时,应该这样访问第一个字符串的第i个字符:word1[i - 1]
  总的来说dp的定义可能和数组访问下标不一样。

if(word1[i - 1] == word2[j - 1])dp[i][j] = ···

我们还需要这样思考:为什么要使用动态规划?不使用其他方法?为什么动态规划可以解决?

1.最长回文子串

LeetCode:5.最长回文子串
在这里插入图片描述
一个回文串 s t r [ i ] [ j ] str[i][j] str[i][j]的子串有这样的性质: s t r [ i + 1 ] [ j − 1 ] str[i+1][j-1] str[i+1][j1]也是回文串。

因此我们要判断一个子串 s t r [ i ] [ j ] str[i][j] str[i][j]是否是回文串,我们只需要知道其子串 s t r [ i + 1 ] [ j − 1 ] str[i+1][j-1] str[i+1][j1]是否是回文串即可。我们使用 d p [ i ] [ j ] dp[i][j] dp[i][j]保存该区间[i,j]是否是回文串。

这样我们就使用回文字符串常用的解题方式——从长度为1的子串开始判断是否为回文串,判断完后长度加一,这样每次都能保证判断时,其子串都已经知道是否是回文串了。

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

class Solution {
public:string longestPalindrome(string s) {vector<vector<bool>> dp(s.size(), vector<bool>(s.size(), false));//dp[i]表示以i结尾的 最长回文子串dp[0][0] = true;int left = 0, len = 1;for(int j = 1; j < s.size(); ++ j){int tmp = j - 1;dp[j][j] = true;if(s[tmp] == s[j]) {dp[tmp][j] =true;left = tmp; len = 2;}}for(int i = 2; i < s.size(); ++ i){//距离for(int j = i; j < s.size(); ++ j){int tmp = j - i;if(s[j] == s[tmp] ){if(dp[tmp + 1][j - 1] == true) {dp[tmp][j] = true;left = tmp; len = i + 1;}}}}return s.substr(left, len);} 
};

2.最长回文子序列

LeetCode:2.最长回文子序列
在这里插入图片描述
与最长回文子串类似,本题的区别是,不要求子串严格是回文串,只需要包含回文串即可。

因此我们要判断一个子串 s t r [ i ] [ j ] str[i][j] str[i][j]是否包含回文串,我们只需要知道其子串 s t r [ i + 1 ] [ j − 1 ] str[i+1][j-1] str[i+1][j1]是否包含回文串即可。我们使用 d p [ i ] [ j ] dp[i][j] dp[i][j]保存该区间[i,j]是包含的最长回文串长度。

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

class Solution {
public:int longestPalindromeSubseq(string s) {int n = s.length();if(n == 1) return 1;vector<vector<int>> dp(n, vector<int>(n));for(int i = 0; i < n; ++ i) {dp[i][i] = 1;}for(int i = 1; i < n; ++ i){for(int j = i; j < n; ++ j){int l = j - i;char c1 = s[l], c2 = s[j];if(c1 == c2){dp[l][j] = dp[l + 1][j - 1] + 2;}else{dp[l][j] = max(dp[l][j - 1], dp[l + 1][j]);}}}return dp[0][n - 1];}
};

3.单词拆分

LeetCode:139. 单词拆分
在这里插入图片描述
这个拼接的顺序不是随便的,比如 c a t s a n d catsand catsand,字典为 [ " c a t " , " c a t s " , " a n d " ] ["cat","cats","and"] ["cat""cats""and"],如果先用 " c a t " "cat" "cat"去拼接,会导致问题无解,但实际上有解。

定义 d p [ i ] dp[i] dp[i]表示,前 i i i个字符是否可以被拼接,那么它能被拼接的话,我们用字典里面的词一个一个放到末尾,然后看 d p [ i − d i c t . s i z e ( ) ] dp[i - dict.size()] dp[idict.size()]能否被拼接就能知道 d p [ i ] dp[i] dp[i]能否被拼接了。

class Solution {
public:bool wordBreak(string s, vector<string>& wordDict) {vector<bool> dp(s.size() + 1, false);dp[0] = true;for(int i = 1; i <= s.size(); ++ i)for(auto & str : wordDict)if(str.size() <= i && dp[i - str.size()] == true)if(s.substr(i - str.size(), str.size()) == str){dp[i] = true;break;}return dp[s.size()];}
};

4.编辑距离

LeetCode:72.编辑距离
在这里插入图片描述
其实动态规划问题就是思考出状态以及状态转移,比如这里你想要知道 w o r d 1 word1 word1 w o r d 2 word2 word2转换次数,你就只需要知道其子串。

if(word1[i - 1] == word2[j - 1]){dp[i][j] = dp[i - 1][j - 1];
}else{dp[i][j] = min(dp[i - 1][j], min(dp[i][j - 1], dp[i - 1][j - 1])) + 1;
}
class Solution {
public:int minDistance(string word1, string word2) {vector<vector<int>> dp(word1.size() + 1, vector<int>(word2.size() + 1));for(int i = 1; i <= word1.size(); ++ i){dp[i][0] = i;}for(int i = 1; i <= word2.size(); ++ i){dp[0][i] = i;}for(int i = 1; i <= word1.size(); ++ i){for(int j = 1; j <= word2.size(); ++ j){if(word1[i - 1] == word2[j - 1]){dp[i][j] = dp[i - 1][j - 1];}else{dp[i][j] = min(dp[i - 1][j], min(dp[i][j - 1], dp[i - 1][j - 1])) + 1;}}}return dp[word1.size()][word2.size()];}
};

5. 共同点和思路

这些字符串相关的动态规划问题有一些共同的特点:

  1. 定义状态

    • 使用二维数组 dp 表示两个子串之间的某种状态(如是否回文、最长子序列长度、是否可以拼接、编辑距离等)。
  2. 状态转移

    • 根据问题的具体要求,定义状态转移方程,用子问题的解构建原问题的解。
  3. 初始化

    • 根据问题的初始条件,初始化 dp 数组的边界值。
  4. 遍历顺序

    • 通常使用双重循环遍历所有可能的子串或子序列。

6. 各个问题的思路和扩展

1. 最长回文子串

思路

  • 定义 dp[i][j] 表示字符串 s 从第 i 到第 j 的子串是否为回文串。
  • 如果 s[i] == s[j],并且 dp[i+1][j-1] 为真,则 dp[i][j] 为真。
  • 初始化单个字符的子串和长度为2的子串。

扩展

  • 可以使用中心扩展法来优化时间复杂度,从每个字符和字符间隙向两边扩展检查回文。

2. 最长回文子序列

思路

  • 定义 dp[i][j] 表示字符串 s 从第 i 到第 j 的子串中最长回文子序列的长度。
  • 如果 s[i] == s[j],则 dp[i][j] = dp[i+1][j-1] + 2
  • 否则,dp[i][j] = max(dp[i+1][j], dp[i][j-1])

扩展

  • 可以尝试空间优化,将二维数组优化为一维数组。

3. 单词拆分

思路

  • 定义 dp[i] 表示字符串 s 的前 i 个字符能否被拆分成字典中的单词。
  • 对于每个位置 i,检查从 ji 的子串是否在字典中,并且 dp[j] 是否为真。

扩展

  • 可以使用记忆化搜索或递归的方法来优化复杂度。

4. 编辑距离

思路

  • 定义 dp[i][j] 表示将 word1 的前 i 个字符转换为 word2 的前 j 个字符所需的最少操作数。
  • 如果 word1[i-1] == word2[j-1],则 dp[i][j] = dp[i-1][j-1]
  • 否则,dp[i][j] = min(dp[i-1][j], dp[i][j-1], dp[i-1][j-1]) + 1

扩展

  • 可以尝试空间优化,将二维数组优化为一维数组。
  • 可以扩展到其他字符串变换问题,如最长公共子序列。

相关文章:

力扣 | 动态规划 | 在字符串的应用 | 最长回文子串、最长回文子序列、单词拆分、编辑距离

文章目录 1.最长回文子串2.最长回文子序列3.单词拆分4.编辑距离5. 共同点和思路6. 各个问题的思路和扩展1. 最长回文子串2. 最长回文子序列3. 单词拆分4. 编辑距离 在解答字符串动态规划的应用时&#xff0c;我们需要非常注意一个问题&#xff1a;   有时候我们定义 d p [ i …...

【docker】docker容器部署常用服务

1、容器部署nginx&#xff0c;并且新增一个页面 docker run -d -p 81:80 --name nginx2 nginx docker exec -it nginx2 /bin/bashcd /usr/share/nginx/html/ echo "hello world">>hello.html2、容器部署redis&#xff0c;成功部署后向redis中添加一条数据 do…...

CentOS 7.6 安装 Weblogic

注&#xff1a;本教程是以虚拟机作为安装环境&#xff0c;如果您公司需要安装 Weblogic 服务器&#xff0c;请先以虚拟机模拟安装一遍&#xff0c;否则出现失误&#xff0c;概不负责&#x1f601;。 一、环境 虚拟机&#xff1a;VMware Workstation 16 Linux&#xff1a;Cent…...

一键清除电脑隐私痕迹,Privacy Eraser助你轻松搞定!

前言 在数字时代&#xff0c;隐私就像是我们手中的细沙&#xff0c;不经意间就可能从指缝间溜走&#xff1b;你是否也曾担心&#xff0c;自己的每一次点击、每一次浏览&#xff0c;都可能成为别人眼中的“秘密”&#xff1f;别急&#xff0c;今天小江湖就要带你走进一款神秘的…...

火语言RPA桌面元素库使用方法

使用火语言RPA自动选取工具获得桌面中元素&#xff1a; 工具标识 桌面 分组下组件若有此标识&#xff0c;则包含选择元素工具&#xff0c;点击此标识会进行选择元素操作。 桌面元素库介绍 ① 根据元素名称筛选元素库中保存的元素 ② 元素库&#xff0c;显示已经保存的元素名…...

FTP.JBoss,Ldap,Rsync未授权访问漏洞(附带修复方法)

一.FTP未授权访问漏洞(匿名登陆) FTP 弱⼝令或匿名登录漏洞&#xff0c;⼀般指使⽤ FTP 的⽤户启⽤了匿名登录功能&#xff0c;或系统⼝令的⻓度太短、复杂度不够、仅包含数字、或仅包含字⺟等&#xff0c;容易被⿊客攻击&#xff0c;发⽣恶意⽂件上传或更严重的⼊侵⾏为。 漏…...

全新在线客服系统源码(pc+h5+uniapp+公众号小程序+抖音)附搭建接入教程

全新在线客服系统源码介绍 一、系统概述与优势 本系统是一款基于PHP的开源在线客服系统&#xff0c;支持PC端、移动端&#xff08;小程序&#xff09;、H5页面以及Uniapp多端接入。系统利用网络技术和人工智能技术&#xff0c;实现用户与客服人员的即时聊天沟通&#xff0c;有…...

为具有公网IPV6地址的服务器安装nextcloudAIO并使用NginxProxyManager配置反向代理

软件和硬件环境 ubuntu server 24.04&#xff0c;并已配置好ipv6公网地址&#xff0c;已安装好docker和docker-compose。一块单独的硬盘&#xff0c;用于单独存储nextcloud数据。&#xff08;非必需&#xff09;有一个能够正常解析的域名&#xff0c;并已配置好AAAA记录解析。…...

挖矿宝藏之TCP/IP

目录 一、TCP/IP简介 1.TCP自述 2.IP自述 二、TCP/IP 寻址 1.IP V6 2.域名 三、TCP/IP协议 一、TCP/IP简介 TCP/IP 指传输控制协议/网际协议&#xff08;Transmission Control Protocol / Internet Protocol&#xff09;&#xff0c;是供已连接因特网的计算机进行通信的…...

略谈set与map的pair封装与进入哈希

引子&#xff1a;之前我们讲了红黑树的自实现&#xff0c;与小小的接口实现&#xff0c;那set与map的pair封装是如何实现的呢&#xff1f;&#xff0c;今天我们来一探究竟&#xff0c;而且我们也要进入新章节--哈希 对于operator--()的封装&#xff1a; 注意&#xff1a;牢记思…...

android13 串口编号修改 串口名修改

总纲 android13 rom 开发总纲说明 目录 1.前言 2.技术分析 别名定义的语法规则 3.修改示例 使用别名 注意事项 4.不生效分析 5.编译查看 6.其他方法 7.彩蛋 1.前言 更改Android设备的串口编号涉及对系统深层次的配置进行修改,通常是为了解决硬件兼容性问题或满足特…...

工作中常用的软件竟可直接下载0.5m卫星影像(Esri影像、天地图、星图)、DEM、土地覆盖数据...

之前我们有介绍过在ArcGIS通过插件、WTMS或者lyr添加谷歌影像、天地图等各种在线图源。今天我们就来再整理一套既方便查看又方便下载的教程&#xff0c;软件就是我们常用的Global Mapper&#xff0c;有点强。 这里我们整理了一些我们工作学习中常用的一些数据下载方法&#xf…...

1章3节:R 语言的产生与发展轨迹

R语言诞生于1990年代,由统计学家Ross Ihaka和Robert Gentleman在新西兰奥克兰大学开发,旨在提供一种免费开源、灵活强大的统计编程工具。R语言基于S语言的设计理念,并通过其开源社区的贡献迅速发展,形成了庞大的生态系统,包括CRAN、RStudio和Shiny等。R语言以其强大的统计…...

html常用标签

一、无序列表 ul li 注意事项&#xff1a;ul下面不可以嵌套其他标签&#xff0c;li下可以 二、有序列表 ol li 注意事项同无序列表 三、自定义列表 dd dt 注意事项同无序列表 四 、表格 table tr&#xff1a;行 th:表头 td:内容 4.1合并单元格 步骤 1.明确合并的目标 2.保留…...

选择文件鼠标右键自定义菜单

注册表路径 计算机\HKEY_CLASSES_ROOT\*\shell 效果 操作 1.定位 winr&#xff0c;输入regedit, 地址栏输入以下路径&#xff0c;并回车。 计算机\HKEY_CLASSES_ROOT\*\shell 2.在shell上右键&#xff0c;新建项 3右键新建字符串值&#xff0c;Icon,Position 4 右键新建c…...

Linux安全与高级应用(九)Linux远程访问与控制:安全与最佳实践

文章目录 Linux远程访问与控制&#xff1a;安全与最佳实践引言一、SSH服务的基本概述二、密钥对验证的SSH体系三、TCP Wrappers的使用四、构建安全的SSH服务实践五、结论 &#x1f44d; 个人网站&#xff1a;【 洛秋导航】【洛秋资源小站】 Linux远程访问与控制&#xff1a;安全…...

前端已经学会vue,做粒子效果

目录 1. Canvas API 2. WebGL 3. 粒子系统 4. 动画与性能优化 5. 现有库和框架 6. Vue 组件和状态管理 实践项目建议 案例1 案例2雪花 已经熟悉了 Vue、TypeScript 和 JavaScript&#xff0c;下面是一些你可以学习的内容&#xff0c;以帮助你实现粒子效果的界面&#…...

Nessus——全面的漏洞扫描神器

一、引言 在网络安全的领域中&#xff0c;及时发现和评估系统中的漏洞是保障网络安全的关键步骤。Nessus 作为一款备受认可的漏洞扫描工具&#xff0c;为企业和安全专业人员提供了强大而全面的漏洞检测和评估功能。本文将深入介绍 Nessus 的特点、功能、使用方法以及其在实际应…...

自动化部署的艺术:Conda包依赖管理的终极指南

标题&#xff1a;自动化部署的艺术&#xff1a;Conda包依赖管理的终极指南 在当今快速发展的科学计算和数据分析领域&#xff0c;Conda已成为Python开发者和数据科学家的首选包管理器之一。它不仅能够管理Python包&#xff0c;还能处理不同语言环境的依赖关系&#xff0c;确保…...

详解Xilinx FPGA高速串行收发器GTX/GTP(7)--IBERT IP核的使用

目录 1、什么是IBERT? 2、IBERT IP核的使用 3、Example Design的使用 4、IBERT的测试 4.1、误码率测试 4.2、眼图测试 4.3、回环测试(Loopback) 5、源码下载 文章总目录点这里:《FPGA接口与协议》专栏的说明与导航 1、什么是IBERT? IBERT就是Xilinx提…...

边缘计算医疗风险自查APP开发方案

核心目标:在便携设备(智能手表/家用检测仪)部署轻量化疾病预测模型,实现低延迟、隐私安全的实时健康风险评估。 一、技术架构设计 #mermaid-svg-iuNaeeLK2YoFKfao {font-family:"trebuchet ms",verdana,arial,sans-serif;font-size:16px;fill:#333;}#mermaid-svg…...

解决Ubuntu22.04 VMware失败的问题 ubuntu入门之二十八

现象1 打开VMware失败 Ubuntu升级之后打开VMware上报需要安装vmmon和vmnet&#xff0c;点击确认后如下提示 最终上报fail 解决方法 内核升级导致&#xff0c;需要在新内核下重新下载编译安装 查看版本 $ vmware -v VMware Workstation 17.5.1 build-23298084$ lsb_release…...

iPhone密码忘记了办?iPhoneUnlocker,iPhone解锁工具Aiseesoft iPhone Unlocker 高级注册版​分享

平时用 iPhone 的时候&#xff0c;难免会碰到解锁的麻烦事。比如密码忘了、人脸识别 / 指纹识别突然不灵&#xff0c;或者买了二手 iPhone 却被原来的 iCloud 账号锁住&#xff0c;这时候就需要靠谱的解锁工具来帮忙了。Aiseesoft iPhone Unlocker 就是专门解决这些问题的软件&…...

定时器任务——若依源码分析

分析util包下面的工具类schedule utils&#xff1a; ScheduleUtils 是若依中用于与 Quartz 框架交互的工具类&#xff0c;封装了定时任务的 创建、更新、暂停、删除等核心逻辑。 createScheduleJob createScheduleJob 用于将任务注册到 Quartz&#xff0c;先构建任务的 JobD…...

初学 pytest 记录

安装 pip install pytest用例可以是函数也可以是类中的方法 def test_func():print()class TestAdd: # def __init__(self): 在 pytest 中不可以使用__init__方法 # self.cc 12345 pytest.mark.api def test_str(self):res add(1, 2)assert res 12def test_int(self):r…...

rnn判断string中第一次出现a的下标

# coding:utf8 import torch import torch.nn as nn import numpy as np import random import json""" 基于pytorch的网络编写 实现一个RNN网络完成多分类任务 判断字符 a 第一次出现在字符串中的位置 """class TorchModel(nn.Module):def __in…...

Unsafe Fileupload篇补充-木马的详细教程与木马分享(中国蚁剑方式)

在之前的皮卡丘靶场第九期Unsafe Fileupload篇中我们学习了木马的原理并且学了一个简单的木马文件 本期内容是为了更好的为大家解释木马&#xff08;服务器方面的&#xff09;的原理&#xff0c;连接&#xff0c;以及各种木马及连接工具的分享 文件木马&#xff1a;https://w…...

Webpack性能优化:构建速度与体积优化策略

一、构建速度优化 1、​​升级Webpack和Node.js​​ ​​优化效果​​&#xff1a;Webpack 4比Webpack 3构建时间降低60%-98%。​​原因​​&#xff1a; V8引擎优化&#xff08;for of替代forEach、Map/Set替代Object&#xff09;。默认使用更快的md4哈希算法。AST直接从Loa…...

Golang——6、指针和结构体

指针和结构体 1、指针1.1、指针地址和指针类型1.2、指针取值1.3、new和make 2、结构体2.1、type关键字的使用2.2、结构体的定义和初始化2.3、结构体方法和接收者2.4、给任意类型添加方法2.5、结构体的匿名字段2.6、嵌套结构体2.7、嵌套匿名结构体2.8、结构体的继承 3、结构体与…...

Chromium 136 编译指南 Windows篇:depot_tools 配置与源码获取(二)

引言 工欲善其事&#xff0c;必先利其器。在完成了 Visual Studio 2022 和 Windows SDK 的安装后&#xff0c;我们即将接触到 Chromium 开发生态中最核心的工具——depot_tools。这个由 Google 精心打造的工具集&#xff0c;就像是连接开发者与 Chromium 庞大代码库的智能桥梁…...