力扣刷题day48|583两个字符串的删除操作、72编辑距离

news2025/7/21 0:24:17

文章目录

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

力扣题目链接

给定两个单词 word1word2 ,返回使得 word1word2 相同所需的最小步数

每步 可以删除任意一个字符串中的一个字符。

示例 1:

输入: word1 = "sea", word2 = "eat"
输出: 2
解释: 第一步将 "sea" 变为 "ea" ,第二步将 "eat "变为 "ea"

示例 2:

输入:word1 = "leetcode", word2 = "etco"
输出:4

动态规划思路一

本题和动态规划:115.不同的子序列基本相同,只要求出两个字符串的最长公共子序列长度即可,那么除了最长公共子序列之外的字符都是必须删除的,最后用两个字符串的总长度减去两个最长公共子序列的长度就是删除的最少步数。

public int minDistance(String word1, String word2) {
    // 初始化
    int[][] dp = new int[word1.length() + 1][word2.length() + 1];

    for (int i = 1; i <= word1.length(); i++) {
        for (int j = 1; j <= word2.length(); j++) {
            if (word1.charAt(i - 1) == word2.charAt(j - 1)) {
                dp[i][j] = dp[i - 1][j - 1] + 1;
            }else {
                dp[i][j] = Math.max(dp[i - 1][j], dp[i][j - 1]);
            }
        }
    }

    return word1.length() + word2.length() - dp[word1.length()][word2.length()] * 2;
}

动态规划思路二

本题和动态规划:115.不同的子序列相比,这次是两个字符串可以相互删了

动态规划五部曲

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

dp[i][j]:以i-1为结尾的字符串word1,和以j-1位结尾的字符串word2,想要达到相等,所需要删除元素的最少次数。

  1. 确定递推公式
  • 当word1[i - 1] 与 word2[j - 1]相同的时候,只有一种情况:

此时说明当前的两个字符相同就不需要删除,就看两个字符串的再往前一个数字是否一样,即dp[i][j] = dp[i - 1][j - 1]

  • 当word1[i - 1] 与 word2[j - 1]不相同的时候,有种情况可以讨论:
    • 情况一:word1[i - 1],此时先对word1做一次删除操作,然后比较的就是word1[i - 2]word2[j - 1],即最少操作次数为dp[i][j] = dp[i - 1][j] + 1
    • 情况二:word2[j - 1],此时先对word2做一次删除操作,然后比较的就是word1[i - 1]word2[j - 2],即最少操作次数为dp[i][j] = dp[i][j - 1] + 1
    • 情况三:同时删word1[i - 1]word2[j - 1],操作的最少次数为dp[i - 1][j - 1] + 2

那最后当然是取最小值,所以当word1[i - 1] 与 word2[j - 1]不相同的时候,递推公式:dp[i][j] = min({dp[i - 1][j - 1] + 2, dp[i - 1][j] + 1, dp[i][j - 1] + 1})

因为dp[i - 1][j - 1] + 1等于 dp[i - 1][j] dp[i][j - 1],这里说明情况三包含在情况一和情况二里面(即可能先删**word1[i-1],再比较word1[i-2]word2[j-1]后删除了word2[j-1];或者是先删word2[j-1],再比较word2[j-2]word1[i-1]后删除了word1[i-1]**)

所以递推公式可简化为:dp[i][j] = min(dp[i - 1][j] + 1, dp[i][j - 1] + 1)

  1. dp数组如何初始化

从递推公式中,可以看出来,dp[i][0] dp[0][j]是一定要初始化的。

dp[i][0]:word2为空字符串,以i-1为结尾的字符串word1要删除多少个元素,才能和word2相同呢,很明显要删除i个字符,即dp[i][0] = i

dp[0][j]的话同理,所以代码如下:

for (int i = 0; i < word1.length() + 1; i++) dp[i][0] = i;
for (int j = 0; j < word2.length() + 1; j++) dp[0][j] = j;
  1. 确定遍历顺序

从递推公式 dp[i][j] = min(dp[i - 1][j - 1] + 2, min(dp[i - 1][j], dp[i][j - 1]) + 1); dp[i][j] = dp[i - 1][j - 1]可以看出dp[i][j]都是根据左上方、正上方、正左方推出来的。

所以遍历的时候一定是从上到下从左到右,这样保证dp[i][j]可以根据之前计算出来的数值进行计算。

  1. 举例推导dp数组

以示例一:word1:“sea”,word2:"eat"为例,推导dp数组状态图如下:

image-20221115123525011

完整代码:

public int minDistance(String word1, String word2) {
    int[][] dp = new int[word1.length() + 1][word2.length() + 1];
    // 初始化
    for (int i = 0; i <= word1.length(); i++) {
        dp[i][0] = i;
    }
    for (int j = 0; j <= word2.length(); j++) {
        dp[0][j] = j;
    }

    for (int i = 1; i <= word1.length(); i++) {
        for (int j = 1; j <= word2.length(); j++) {
            if (word1.charAt(i - 1) == word2.charAt(j - 1)) {
                dp[i][j] = dp[i - 1][j - 1];
            }else {
                dp[i][j] = Math.min(dp[i - 1][j] + 1, dp[i][j - 1] + 1);
            }
        }
    }

    return dp[word1.length()][word2.length()];
}

72. 编辑距离

力扣题目链接

给你两个单词 word1word2请返回将 word1 转换成 word2 所使用的最少操作数

你可以对一个单词进行如下三种操作:

  • 插入一个字符
  • 删除一个字符
  • 替换一个字符

示例 1:

输入:word1 = "horse", word2 = "ros"
输出:3
解释:
horse -> rorse (将 'h' 替换为 'r')
rorse -> rose (删除 'r')
rose -> ros (删除 'e')

示例 2:

输入:word1 = "intention", word2 = "execution"
输出:5
解释:
intention -> inention (删除 't')
inention -> enention (将 'i' 替换为 'e')
enention -> exention (将 'n' 替换为 'x')
exention -> exection (将 'n' 替换为 'c')
exection -> execution (插入 'u')

思路

本体涉及到删除替换插入三个操作,就要分情况思考什么时候删除,什么时候替换以及什么时候插入呢?

动态规划五部曲

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

同样的和上一题相同,定义dp数组为

dp[i][j] 表示以下标i-1为结尾的字符串word1,和以下标j-1为结尾的字符串word2,最近编辑距离为dp[i][j]

  1. 确定递推公式
  • 如果word1[i-1] == word2[j-1],此时不需要任何操作,所以dp[i][j] = dp[i-1][j-1]

  • 如果word1[i-1] != word2[j-1],此时可以分为种情况:

    • 操作一:删除。word1删除一个元素,那么就是以下标i - 2为结尾的word1 与 j-1为结尾的word2的最近编辑距离,再加上一个操作,即 dp[i][j] = dp[i - 1][j] + 1;

    • 操作二:替换。替换word1[i - 1],使其与word2[j - 1]相同,此时不用增加元素,替换完后word1[i - 1]word2[j - 1]就一样的了。那么此时的编辑距离就是以下标i-2为结尾的word1 与 j-2为结尾的word2的最近编辑距离,加上一个替换元素的操作,即 dp[i][j] = dp[i - 1][j - 1] + 1;

    • 操作二:插入。在word1[i - 1]后面插入一个与word2[j - 1]相同的字符,此时要比较word2[i - 1]的前一个字符word2[i - 2]与当前的word1[i - 1]的关系(看他们的编辑距离),加上一个插入元素的操作,即 dp[i][j] = dp[i][j - 1] + 1;

三种情况取最小值,即:dp[i][j] = min({dp[i - 1][j], dp[i - 1][j - 1], dp[i][j - 1]}) + 1;

  1. dp数组如何初始化

再回顾一下dp[i][j]的定义:dp[i][j] 表示以下标i-1为结尾的字符串word1,和以下标j-1为结尾的字符串word2,最近编辑距离为dp[i][j]

dp[i][0] = iword1(0~i-1)要把其中的元素全部删除才能和此时为空集word2相同,所以要删除i次。

dp[0][j] = jword2(0~j-1)要把其中的元素全部删除才能和此时为空集word1相同,所以要删除j次。

for (int i = 1; i <= m; i++) {
    dp[i][0] =  i;
}
for (int j = 1; j <= n; j++) {
    dp[0][j] = j;
}
  1. 确定遍历顺序

由四个递推公式可以知道:

  • dp[i][j] = dp[i - 1][j - 1]
  • dp[i][j] = dp[i][j - 1] + 1
  • dp[i][j] = dp[i - 1][j - 1] + 1
  • dp[i][j] = dp[i - 1][j] + 1

可以看出dp[i][j]是依赖左方,上方和左上方元素的

image-20221115132136814

所以一定是从左到右从上到下去遍历。

  1. 举例推导dp数组

以示例1为例,输入:word1 = “horse”, word2 = "ros"为例,dp矩阵状态图如下:

image-20221115132038333

完整代码:

public int minDistance(String word1, String word2) {
    int[][] dp = new int[word1.length() + 1][word2.length() + 1];
    // 初始化
    for (int i = 0; i <= word1.length(); i++) {
        dp[i][0] = i;
    }
    for (int j = 0; j <= word2.length(); j++) {
        dp[0][j] = j;
    }

    for (int i = 1; i <= word1.length(); i++) {
        for (int j = 1; j <= word2.length(); j++) {
            if (word1.charAt(i - 1) == word2.charAt(j - 1)) {
                dp[i][j] = dp[i - 1][j - 1];
            }else {
                dp[i][j] = Math.min(Math.min(dp[i - 1][j] + 1, dp[i - 1][j - 1] + 1), dp[i][j - 1] + 1);
            }
        }
    }

    return dp[word1.length()][word2.length()];
}

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

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

相关文章

K_A05_001 基于 STM32等单片机驱动8X8点阵模块(MAX7219)显示0-9

目录 一、资源说明 二、基本参数 1、参数 2、引脚说明 三、通信协议说明 工作时序 对应程序: 四、部分代码说明 1、接线说明 1.1、STC89C52RC8X8点阵模块&#xff08;MAX7219&#xff09; 1.2、STM32F103C8T68X8点阵模块&#xff08;MAX7219&#xff09; 2、亮度调节 五、基…

Python中内置数据库!SQLite使用指南!

&#x1f4a1; 作者&#xff1a;韩信子ShowMeAI &#x1f4d8; Python3◉技能提升系列&#xff1a;https://www.showmeai.tech/tutorials/56 &#x1f4d8; 本文地址&#xff1a;https://www.showmeai.tech/article-detail/390 &#x1f4e2; 声明&#xff1a;版权所有&#xf…

Docker数据卷

Docker数据卷、Docker安全Docker数据卷Docker数据卷管理bind mountdocker数据卷两种方式不同和相同卷插件简介convoy卷插件实践Docker数据卷 主要解决存储问题、容器数据滞留 Docker数据卷管理 bind mount “-v”宿主机路径容器内nginx发布目录 新建一个首页 现在容器内目录…

猿创征文|工具百宝箱-编辑器-笔记工具-日常小工具-原型设计工具

这篇文主要介绍了开发者工具之外的一些日常小工具&#xff0c;我用这些小工具主要完成什么工作。分享给大家 官方活动入口&#xff1a;「猿创征文 」第四季 | 2022 年我的开发者工具 猿创征文&#xff5c;工具百宝箱-代码编辑器-版本控制工具-终端神器-项目与事务跟踪工具-SFTP…

pdf文件转txt怎么转?这几个方法你值得收藏

平时我们在网络上搜索资料的时候&#xff0c;会发现很多资料都是以PDF格式显示的&#xff0c;虽然这种文件格式很方便我们查看&#xff0c;但是如果将其保存到手机中&#xff0c;又太占用内存了。其实我们可以将其转换成txt格式&#xff0c;因为我发现它不仅不占空间&#xff0…

助力数据中心双碳发展,存储如何变得越来越绿?

2022年11月10日&#xff0c;我看到曙光发了首款液冷存储&#xff0c;目标锁定数据中心PUE1.1以下。在“双碳”发展趋势下&#xff0c;聚焦液冷存储与液冷服务器的创新&#xff0c;曙光对绿色数据中心的可持续发展将带来行业引领效应。 双碳大趋势下&#xff0c;绿色存储呼之欲出…

计算机网络复习

考试重点 要掌握OSI七层模型&#xff0c; 会根据数据画模拟和数字信号的图&#xff0c;尤其是TCP和UDP所提供的服务&#xff0c; 掌握TCP连接建立和释放的完整过程&#xff0c; 掌握滑动窗口的概念&#xff0c; 还要了解端到端的含义&#xff0c; 了解ARP、ICMP、CIDR等协议的…

干了3年软件测试,2022年我离职了...

今天在网上刷到一个帖子&#xff0c;说软件测试岗&#xff0c;在公司呆了三年&#xff0c;由于疫情原因&#xff0c;公司效益不是很好&#xff0c;加上自己的技术一直停留在功能测试&#xff0c;在公司可有可无&#xff0c;被公司裁后找不到工作… 逛百度贴吧、逛技术论坛&…

[附源码]java毕业设计基于servlet技术实现游戏娱乐平台

项目运行 环境配置&#xff1a; Jdk1.8 Tomcat7.0 Mysql HBuilderX&#xff08;Webstorm也行&#xff09; Eclispe&#xff08;IntelliJ IDEA,Eclispe,MyEclispe,Sts都支持&#xff09;。 项目技术&#xff1a; SSM mybatis Maven Vue 等等组成&#xff0c;B/S模式 M…

FFplay文档解读-48-多媒体过滤器二

32.8 ebur128 EBU R128扫描仪滤光片。此过滤器将音频流作为输入并以不变的方式输出。默认情况下&#xff0c;它以10Hz的频率记录消息&#xff0c;具有瞬时响度&#xff08;由M标识&#xff09;&#xff0c;短期响度&#xff08;S&#xff09;&#xff0c;集成响度&#xff08;…

简单工厂,工厂方法,抽象工厂模式

软件设计七大原则 一、简单工厂&#xff08;静态工厂方法&#xff09; 它存在的目的很简单&#xff1a;定义一个创建对象的接口。组成&#xff1a; 工厂类角色&#xff1a;这是本模式的核心&#xff0c;含有一定的商业逻辑和判断逻 辑。在java中它往往由一个具体类实现。 抽…

南非醉茄来源的天然产物之活性大盘点

图 1. 南非醉茄 (Withania Somnifera) 的多种药理活性[2] 化学成分 到目前为止&#xff0c;大约有超过 12 种生物碱和 40 多种甾体内脂类化合物从南非醉茄中被分离出来 。其中&#xff0c;醉茄内脂 (Withanolides) 因其广泛的药理活性 (抗肿瘤、抗菌、抗炎和免疫调节活性等) 受…

RabbitMQ系列【9】过期时间

有道无术&#xff0c;术尚可求&#xff0c;有术无道&#xff0c;止于术。 文章目录概念队列过期控制台代码消息过期删除策略概念 TTL全称Time To Live&#xff0c;是指存活时间或过期时间。当消息到达存活时间后&#xff0c;还没有被消费&#xff0c;会被自动清除。 RabbitMQ…

二十六、设置时序电路初始状态的方法(初始值设置)

----------------------------------------------------------------------------------------------------- 该专栏主要介绍用场效应管设计基本电路,由浅到深,从用场效应管设计最基本的非门、与非门、或非门、与门、或门的设计,到用场效应管设计触发,再到用场效应管设计具…

【论文阅读】Combinatorial Benders’ Cuts for the Strip Packing Problem

文章目录一、摘要二、求解条形装箱的Benders分解2.1 Notation2.2 SPP的数学逻辑模型2.3 分解方法三、从问题的解决方案3.1 复杂性分析3.2 y-check的算法3.2.1 预处理过程3.2.1.1 Merge Items 合并项目3.2.1.2 Lift Item Widths 增大项目宽度3.2.1.3 Shrink the Strip 缩小长条容…

实战+代码!Selenium + Phantom JS爬取天天基金数据

功能&#xff1a; 通过程序实现从基金列表页&#xff0c;获取指定页数内所有基金的近一周收益率以及每支基金的详情页链接。再进入每支基金的详情页获取其余的基金信息&#xff0c;将所有获取到的基金详细信息按近6月收益率倒序排列写入一个Excel表格。 思路&#xff1a; 通过…

python-pandas用法大全

目录1 修改 DataFrame 某一列的数据类型2 读取和保存3 特定值的替换4 两个 DataFrame 的连接4.1 join4.2 某列作为拼接的依据5 删除某一列5.1 删除第n列5.2 删除特定名称列6 行、列重排6.1列重排6.2 行重排6.3 根据某一列的值排序6.4 随机打乱所有行7 修改某列的名称7.1 全局修…

m基于自适应门限软切换的3G和Wifi垂直切换算法的matlab仿真

目录 1.算法概述 2.仿真效果预览 3.核心MATLAB预览 4.完整MATLAB程序 1.算法概述 这里还是考虑位置信息和强度联合切换判决的方法&#xff0c;如果你的设备没法提供具体的位置信息的话&#xff0c;那么就把位置信息的权值设置为0。强度判决的权值设置为1即可。 需要传输的数…

外业精灵,在水土流失监测野外调查工作中的应用

常规的水土流失野外调查技术已难以满足现阶段区域水土流失监测工作的需求。 为探索高效、精准、高质量的水土流失数据采集技术&#xff0c;作者以山东沂蒙山泰山国家级重点治理区蒙阴县为例&#xff0c;以小流域或公里网格为调查单元&#xff0c;通过分析外业精灵的技术优势&a…

webpack高级配置

摇树&#xff08;tree shaking&#xff09; 我主要是想说摇树失败的原因&#xff08;tree shaking 失败的原因&#xff09;&#xff0c;先讲下摇树本身效果 什么是摇树&#xff1f; 举个例子 首先 webpack.config.js配置 const webpack require("webpack");/**…