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

代码随想录Day 45|leetcode题目:115.不同的子序列、583. 两个字符串的删除操作、72. 编辑距离

提示:DDU,供自己复习使用。欢迎大家前来讨论~

文章目录

  • 题目
    • 题目一: 115.不同的子序列
      • 解题思路:
      • 1. 确定dp数组(dp table)以及下标的含义
      • 2. 确定递推公式
      • 3. dp数组如何初始化
      • 4. 确定遍历顺序
      • 5. 举例推导dp数组
      • 代码实现
    • 题目二:583. 两个字符串的删除操作
      • 解题思路:
      • 1. 确定dp数组(dp table)以及下标的含义
      • 2. 确定递推公式
      • 3. dp数组如何初始化
      • 4. 确定遍历顺序
      • 5. 举例推导dp数组
      • 代码实现
      • 动态规划二(求最长公共子序列)
      • 代码实现
    • 题目三:72. 编辑距离
      • 解题思路
      • 1. 确定dp数组(dp table)以及下标的含义
      • 2. 确定递推公式
      • 3. dp数组如何初始化
      • 4. 确定遍历顺序
      • 5. 举例推导dp数组
      • 代码实现
    • 编辑距离总结篇
      • 编辑距离问题

动态规划Part12

题目

题目一: 115.不同的子序列

115. 不同的子序列

解题思路:

这道题目要求判断字符串s是否包含字符串t作为子序列。这里的子序列指的是,t的字符可以不连续,但顺序必须保持一致。解题思路使用动态规划,具体步骤如下:

1. 确定dp数组(dp table)以及下标的含义

定义二维数组dp[i][j],其中dp[i][j]表示以s的前i-1个字符为结尾的子序列中,出现以t的前j-1个字符为结尾的子序列的个数。

2. 确定递推公式

根据s[i - 1]t[j - 1]是否相等,分两种情况:

  • 相等dp[i][j] = dp[i - 1][j - 1] + dp[i - 1][j]。因为s[i - 1]可以匹配t[j - 1],也可以不匹配。
  • 不相等dp[i][j] = dp[i - 1][j]。因为s[i - 1]不匹配t[j - 1],只能忽略s[i - 1]

3. dp数组如何初始化

  • dp[i][0] = 1:任何字符串的子序列都至少包含空字符串,所以初始化为1。
  • dp[0][j] = 0:空字符串s不能包含任何非空字符串t作为子序列,所以初始化为0。
  • dp[0][0] = 1:空字符串是自身的子序列。

4. 确定遍历顺序

遍历顺序为从左到右,从上到下,确保每个dp[i][j]的值都是基于已经计算过的dp[i-1][j]dp[i-1][j-1]来计算的。

5. 举例推导dp数组

以具体例子(如s = "baegg"t = "bag")来手动计算dp数组,验证递推公式的正确性。

代码实现

class Solution {
public:int numDistinct(string s, string t) {vector<vector<uint64_t>> dp(s.size() + 1, vector<uint64_t>(t.size() + 1));for (int i = 0; i <= s.size(); i++) dp[i][0] = 1; // 空字符串的子序列计数为1for (int j = 1; j <= t.size(); j++) dp[0][j] = 0; // 空s不能包含非空tfor (int i = 1; i <= s.size(); i++) {for (int j = 1; j <= t.size(); j++) {if (s[i - 1] == t[j - 1]) {dp[i][j] = dp[i - 1][j - 1] + dp[i - 1][j]; // s[i-1]匹配t[j-1]或不匹配} else {dp[i][j] = dp[i - 1][j]; // s[i-1]不匹配t[j-1],忽略s[i-1]}}}return dp[s.size()][t.size()]; // 返回s的所有子序列中包含t的计数}
};

时间复杂度为O(n*m),空间复杂度也为O(n*m),其中n和m分别是字符串s和t的长度。

题目二:583. 两个字符串的删除操作

583. 两个字符串的删除操作

解题思路:

这道题目要求找出将两个字符串转换为彼此所需的最少删除次数,可以通过动态规划来解决。以下是详细的解题思路:

1. 确定dp数组(dp table)以及下标的含义

定义二维数组dp[i][j],其中dp[i][j]表示将字符串word1的前i-1个字符和字符串word2的前j-1个字符转换为彼此所需的最少删除次数。

2. 确定递推公式

根据word1[i - 1]word2[j - 1]是否相等,分两种情况:

  • 相等dp[i][j] = dp[i - 1][j - 1]。因为当两个字符相等时,不需要删除这两个字符。
  • 不相等dp[i][j] = min(dp[i - 1][j] + 1, dp[i][j - 1] + 1)。因为当两个字符不相等时,可以选择删除word1的一个字符或者删除word2的一个字符,取两者的最小值。

3. dp数组如何初始化

  • dp[i][0] = i:表示word2为空字符串时,需要删除word1的前i-1个字符。
  • dp[0][j] = j:表示word1为空字符串时,需要删除word2的前j-1个字符。

4. 确定遍历顺序

遍历顺序为从上到下,从左到右,确保每个dp[i][j]的值都是基于已经计算过的dp[i-1][j]dp[i][j-1]来计算的。

5. 举例推导dp数组

以具体例子(如word1 = "sea"word2 = "eat")来手动计算dp数组,验证递推公式的正确性。

代码实现

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

时间复杂度为O(n*m),空间复杂度也为O(n*m),其中n和m分别是字符串word1和word2的长度。

动态规划二(求最长公共子序列)

另一种解法是求两个字符串的最长公共子序列(LCS),然后用两个字符串的总长度减去最长公共子序列的长度的两倍,即为最少删除次数。

代码实现

class Solution {
public:int minDistance(string word1, string word2) {vector<vector<int>> dp(word1.size()+1, vector<int>(word2.size()+1, 0));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] + 1;else dp[i][j] = max(dp[i-1][j], dp[i][j-1]);}}return word1.size()+word2.size()-dp[word1.size()][word2.size()]*2;}
};

时间复杂度为O(n*m),空间复杂度为O(n*m)。


题目三:72. 编辑距离

72. 编辑距离

解题思路

编辑距离问题是一个经典的动态规划问题,用于计算两个字符串之间的最小编辑操作次数,使得一个字符串可以转换成另一个字符串。以下是详细的解题思路:

1. 确定dp数组(dp table)以及下标的含义

定义二维数组dp[i][j],其中dp[i][j]表示以下标i-1为结尾的字符串word1和以下标j-1为结尾的字符串word2之间的最小编辑距离。

2. 确定递推公式

根据word1[i - 1]word2[j - 1]是否相等,分两种情况:

  • 相等:不需要任何编辑操作,即dp[i][j] = dp[i - 1][j - 1]
  • 不相等:需要进行编辑操作,可能的操作包括:
    • 删除word1的一个字符:dp[i - 1][j] + 1
    • 删除word2的一个字符:dp[i][j - 1] + 1
    • 替换word1的一个字符:dp[i - 1][j - 1] + 1
    • 选择最小操作次数:dp[i][j] = min({dp[i - 1][j - 1], dp[i - 1][j], dp[i][j - 1]}) + 1

3. dp数组如何初始化

  • dp[i][0] = i:表示将word1的前i-1个字符转换为一个空字符串需要删除i次。
  • dp[0][j] = j:表示将一个空字符串转换为word2的前j-1个字符需要添加j次。

4. 确定遍历顺序

遍历顺序为从上到下,从左到右,确保每个dp[i][j]的值都是基于已经计算过的dp[i-1][j]dp[i][j-1]dp[i-1][j-1]来计算的。

5. 举例推导dp数组

以具体例子(如word1 = "horse"word2 = "ros")来手动计算dp数组,验证递推公式的正确性。

代码实现

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

时间复杂度为O(n*m),空间复杂度也为O(n*m),其中n和m分别是字符串word1和word2的长度。

编辑距离总结篇

  1. 判断子序列:判断一个字符串是否为另一个字符串的子序列,只涉及删除操作。
  2. 不同的子序列:计算一个字符串在另一个字符串子序列中出现的次数,涉及删除操作。
  3. 两个字符串的删除操作:计算使两个字符串相同的最少删除次数,涉及两个字符串的删除操作。

编辑距离问题

问题定义:给定两个字符串word1word2,计算将word1转换成word2的最少操作数,操作包括插入、删除和替换。

相关文章:

代码随想录Day 45|leetcode题目:115.不同的子序列、583. 两个字符串的删除操作、72. 编辑距离

提示&#xff1a;DDU&#xff0c;供自己复习使用。欢迎大家前来讨论~ 文章目录 题目题目一&#xff1a; 115.不同的子序列解题思路&#xff1a;1. 确定dp数组&#xff08;dp table&#xff09;以及下标的含义2. 确定递推公式3. dp数组如何初始化4. 确定遍历顺序5. 举例推导dp数…...

浮点数在内存中的存储详解(超详细)

目录 1. 浮点数存储规则 2. IEEE754规定&#xff1a; 3. 关于M的说明&#xff1a; 4. 关于E的说明&#xff1a; 5. 关于S的说明&#xff1a; 6.浮点数从内存中取出&#xff08;三种情况&#xff09; 情况1&#xff1a;E不全为0或不全为1 情况2&#xff1a;E全为0 情况3&a…...

Maven下载安装

下载 下载地址&#xff1a;Maven – Download Apache Maven 选择合适的版本进行下载 windows&Linux安装 1, 解压apache-maven-3.6.1.rar即安装完成 2&#xff0c; 配置环境变量MAVEN_HOME为安装路径&#xff0c;并将MAVEN_HOME的bin目录配置到PATH下 3&#xff0c;…...

Qt:Q_GLOBAL_STATIC实现单例(附带单例使用和内存管理)

前言 本文主要写Q_GLOBAL_STATIC实现单例以及单例的释放&#xff0c;网上很多教程只有单例的创建&#xff0c;但是并没有告诉我们单例的内存管理&#xff0c;这就很头疼。 正文 使用 Qt 的 Q_GLOBAL_STATIC // Singleton.h #ifndef SINGLETON_H #define SINGLETON_H#includ…...

URL.createObjectURL 与 FileReader:Web 文件处理两大法宝的对比

URL.createObjectURL 与 FileReader&#xff1a;Web 文件处理两大法宝的对比 在Web开发中&#xff0c;处理用户上传的文件是一项常见且重要的任务。URL.createObjectURL和FileReader是两种常用于此目的的Web API&#xff0c;它们各有特点&#xff0c;适用于不同的场景。本文将…...

零基础考过软考信息系统项目管理师经验分享

选择适合的课程&#xff1a;如果你是零基础&#xff0c;建议找一些专门针对新手的课程&#xff0c;讲解通俗易懂。 刷题至关重要&#xff1a;软考的题库很庞大&#xff0c;多做题是必须的。 做好笔记和复习&#xff1a;上课时要做好笔记&#xff0c;课后及时复习&#xff0c;…...

机器学习课程学习周报十二

机器学习课程学习周报十二 文章目录 机器学习课程学习周报十二摘要Abstract一、机器学习部分1.1 fGAN: General Framework of GAN1.2 CycleGAN1.3 Auto-Encoder1.4 概率论复习&#xff08;一&#xff09; 总结 摘要 本周的学习内容涵盖了fGAN框架、CycleGAN、自编码器以及概率…...

python多线程程序设计 之二

python多线程程序设计 之二 线程同步机制lock对象acquirereleaselocked RLock对象条件变量条件变量应用实列实列代码 线程同步机制 lock对象 原语锁是一种同步原语&#xff0c;锁定时不属于特定线程。在Python中&#xff0c;它是目前可用的最低级别的同步原语&#xff0c;由_…...

k8s用StatefulSet部署redis

redis-config.yaml &#xff08;配置文件&#xff09; apiVersion: v1 kind: ConfigMap metadata:name: redis-config data:redis.conf: |# Redis general configuration​ bind 0.0.0.0 ​ protected-mode no ​ port 6379 ​ dir /data ​ appendonly yesse…...

flink on k8s

1.修改host文件 vi /etc/hosts 添加如下内容 这样搭集群的时候就不用记ip了 #::1 localhost localhost.localdomain localhost6 localhost6.localdomain6127.0.0.1 localhost localhost.localdomain localhost4 localhost4.localdomain4 165.154.221.97 tlb-001 k8s01 k8s-m…...

Java集合(八股)

这里写目录标题 Collection 接口List 接口ArrayList 简述 1. ArrayList 和 LinkedList 区别&#xff1f;⭐️⭐️⭐️⭐️2. ArrayList 和 Array 的区别&#xff1f;⭐️⭐️⭐️ArrayList 和 Vector 区别&#xff1f;⭐️⭐️ArrayList 的扩容机制&#xff1f;⭐️⭐️⭐️ Qu…...

python+adb

#!/usr/bin/python env # -*- coding: utf-8 -*- import os import sys import subprocess from time import sleepimport logging logging.basicConfig(levellogging.DEBUG) class ScreenCapture():def get_screen_size(self):"""获取手机分辨率""&q…...

AIGC文本生成

文本生成是一种人工智能技术&#xff0c;它基于深度学习算法&#xff0c;根据给定的提示信息创作出有逻辑、连贯的文本内容。 文本生成所需的输入&#xff08;提示或Prompt&#xff09;可以是简单的关键词、一句话概述或是更复杂的指令和上下文信息。文本生成模型通过分析大量…...

系统架构设计师教程 第5章 5.4 软件测试 笔记

5.4 软件测试 5.4.1 测试方法 ★★★★★ 软件测试方法的分类有很多种&#xff0c; 以测试过程中程序执行状态为依据可分为静态测试 (Static Testing,ST) 和动态测试 (Dynamic Testing,DT); 以具体实现算法细节和系统内部结构的相关情况为根据可分黑盒测试、白盒测试和灰盒测…...

ASPICE评估全流程解析:汽车软件开发组织能力的系统化评估

ASPICE&#xff08;Automotive SPICE&#xff09;评估的过程是一个系统化和详尽的流程&#xff0c;旨在评估汽车软件开发组织在软件开发过程方面的能力。 以下是ASPICE评估过程的详细描述&#xff1a; 1. 评估准备阶段 a. 确定评估目标和范围 明确评估的目标&#xff0c;如评…...

合并RAR分卷压缩包

因为文件压缩之后体积仍然过大&#xff0c;大家可能会选择进行分卷压缩&#xff0c;那么rar分卷压缩包之后如何合并成一个压缩包文件呢&#xff1f;今天我们来学习rar分卷压缩包&#xff0c;合并成一个的方法。 最基础的方法就是将分卷压缩包解压出来之后&#xff0c;再将文件…...

重生奇迹MU 想去哪就去哪玩 轻松玩转翅膀属性

在重生奇迹MU这个游戏中&#xff0c;玩家需要扫荡各种怪物&#xff0c;勇斗BOSS&#xff0c;与其他玩家激战。在这个充满冒险的旅程中&#xff0c;翅膀是最重要的装备之一。拥有一个属性强大的翅膀&#xff0c;代表着玩家的成长与强大。穿上它&#xff0c;加速你的冒险之旅吧&a…...

Lnux-gcc/g++使用

目录 1.gcc/g介绍 1.什么是 gcc / g 2.gcc/g指令格式 2. gcc / g 实现程序翻译的过程 1.预处理(进行宏替换) 2.编译(生成汇编&#xff09; 3.汇编&#xff08;生成机器可识别代码&#xff09; 4.连接&#xff08;生成可执行文件或库文件&#xff09; 1.gcc/g介绍 1.什么…...

用Python创建一个键盘输入捕获程序

目录 简介 环境准备 安装依赖 项目结构 编写代码 1. 导入库 2. 定义回调函数 3. 启动键盘监听器 4. 整合代码 运行程序 结论 简介 在这篇博文中,我们将探索如何使用Python编写一个简单的键盘输入捕获程序。这个程序将实时捕获用户的键盘输入并在控制台中显示出来。…...

Mybatis中Like模糊查询三种处理方式

目录 Mybatis中Like模糊查询三种处理方式 1.通过单引号拼接${} 1&#xff09;mapper接口 2&#xff09;Mapper.xml 3&#xff09;测试代码 4) 测试结果 2.通过concat()函数拼接(个人推荐使用这种) 1&#xff09;mapper接口 2&#xff09;Mapper.xml 3&#xff09;测试代码 4) 测…...

Pixel Language Portal详细步骤:从GitHub源码构建到自定义16-bit图标替换

Pixel Language Portal详细步骤&#xff1a;从GitHub源码构建到自定义16-bit图标替换 1. 项目介绍与准备工作 Pixel Language Portal&#xff08;像素语言跨维传送门&#xff09;是一款基于Tencent Hunyuan-MT-7B翻译引擎构建的创新型翻译工具。它将传统翻译功能与16-bit像素…...

HJ165 小红的优惠券

题目题解(36)讨论(31)排行 入门 通过率&#xff1a;49.28% 时间限制&#xff1a;1秒 空间限制&#xff1a;256M 知识点贪心 校招时部分企业笔试将禁止编程题跳出页面&#xff0c;为提前适应&#xff0c;练习时请使用在线自测&#xff0c;而非本地IDE。 描述 小红的购物车…...

计算机毕业设计:Python城市交通客流预测分析平台 Flask框架 可视化 Requests爬虫 Arima模型 LSTM 深度学习(建议收藏)✅

博主介绍&#xff1a;✌全网粉丝10W,前互联网大厂软件研发、集结硕博英豪成立工作室。专注于计算机相关专业项目实战6年之久&#xff0c;选择我们就是选择放心、选择安心毕业✌ > &#x1f345;想要获取完整文章或者源码&#xff0c;或者代做&#xff0c;拉到文章底部即可与…...

在CentOS 7.9上,我如何用Ollama+DeepSeek-R1+RAGFlow搭建了一个完全离线的AI知识库(保姆级避坑指南)

在CentOS 7.9上构建离线AI知识库&#xff1a;OllamaDeepSeek-R1RAGFlow实战全记录 最近在帮一家金融机构搭建内部知识库时&#xff0c;遇到了一个棘手的需求&#xff1a;所有AI组件必须完全离线运行&#xff0c;且要部署在已经服役5年的CentOS 7.9服务器上。经过两周的折腾&…...

从音频到全身动捕:手把手教你用AudCast和DITs生成带手势的AI视频(附开源项目分析)

从音频到全身动捕&#xff1a;手把手教你用AudCast和DITs生成带手势的AI视频&#xff08;附开源项目分析&#xff09; 在数字内容创作领域&#xff0c;AI视频生成技术正经历从静态图像到动态交互的跨越式发展。传统音频驱动视频方案往往局限于面部表情同步&#xff0c;而全身动…...

响应 (接上文)

在我们前⾯的代码例⼦中&#xff0c;都已经设置了响应数据,Http响应结果可以是数据,也可以是静态⻚⾯,也可 以针对响应设置状态码,Header信息等.返回静态⻚⾯创建前端⻚⾯index.html(注意路径)html代码如下:<!DOCTYPE html> <html lang"en"> <head>…...

宝塔面板安全加固全攻略:从密码重置到IP白名单配置(附常见问题解决)

宝塔面板安全加固全攻略&#xff1a;从密码重置到IP白名单配置&#xff08;附常见问题解决&#xff09; 在公网环境下&#xff0c;服务器安全防护是每个运维人员的必修课。作为国内最受欢迎的服务器管理面板之一&#xff0c;宝塔面板的便捷性与其潜在的安全风险并存。本文将系统…...

计算机毕业设计:Python出行数据智能分析与预测平台 Django框架 可视化 数据分析 PyEcharts 交通 深度学习(建议收藏)✅

博主介绍&#xff1a;✌全网粉丝10W,前互联网大厂软件研发、集结硕博英豪成立工作室。专注于计算机相关专业项目实战6年之久&#xff0c;选择我们就是选择放心、选择安心毕业✌ > &#x1f345;想要获取完整文章或者源码&#xff0c;或者代做&#xff0c;拉到文章底部即可与…...

高性能数据库集群

近年来各种存储技术飞速发展&#xff0c;但关系数据库由于其 ACID 的特性和功能强大的 SQL 查询&#xff0c;目前还是各种业务系统中关键和核心的存储系统&#xff0c;很多场景下高性能的设计最核心的部分就是关系数据库的设计。 不管是为了满足业务发展的需要&#xff0c;还是…...

技术员一键重装工具

链接&#xff1a;https://pan.quark.cn/s/22cfbc52af20...