2021-06-11:给定两个字符串s1和s2,问s2最少删除多少字符可以成为s1的子串? 比如 s1 = “abcde”,s2 = “axbc”。

福大大 答案2021-06-11:

解法一
求出str2所有的子序列,然后按照长度排序,长度大的排在前面。
然后考察哪个子序列字符串和s1的某个子串相等(KMP),答案就出来了。
分析:
因为题目原本的样本数据中,有特别说明s2的长度很小。所以这么做也没有太大问题,也几乎不会超时。
但是如果某一次考试给定的s2长度远大于s1,这么做就不合适了。
str1长度为N,str2长度为M。时间复杂度:O(2的M次方*N)。

解法二
生成所有s1的子串
然后考察每个子串和s2的编辑距离(假设编辑距离只有删除动作且删除一个字符的代价为1)
如果s1的长度较小,s2长度较大,这个方法比较合适。
时间复杂度:O(N * M平方)。

代码用golang编写。代码如下:

package main

import (
"fmt"
"sort"
"strings"
) func main() {
s1 := "abcde"
s2 := "axbc"
ret1 := minCost1(s1, s2)
ret3 := minCost3(s1, s2)
fmt.Println(ret1, ret3)
} // 题目:
// 给定两个字符串s1和s2,问s2最少删除多少字符可以成为s1的子串?
// 比如 s1 = "abcde",s2 = "axbc"
// 返回 1 // 解法一
// 求出str2所有的子序列,然后按照长度排序,长度大的排在前面。
// 然后考察哪个子序列字符串和s1的某个子串相等(KMP),答案就出来了。
// 分析:
// 因为题目原本的样本数据中,有特别说明s2的长度很小。所以这么做也没有太大问题,也几乎不会超时。
// 但是如果某一次考试给定的s2长度远大于s1,这么做就不合适了。
func minCost1(s1 string, s2 string) int {
s2SubsVal := make([]string, 0)
s2Subs := &s2SubsVal
process(s2, 0, "", s2Subs)
//s2Subs.sort(new LenComp());
sort.Slice(*s2Subs, func(i, j int) bool {
return len((*s2Subs)[i]) > len((*s2Subs)[j])
})
for _, str := range *s2Subs {
if strings.Index(s1, str) != -1 { // indexOf底层和KMP算法代价几乎一样,也可以用KMP代替
return len(s2) - len(str)
}
}
return len(s2)
} func process(str2 string, index int, path string, list *[]string) {
if index == len(str2) {
*list = append(*list, path)
return
}
process(str2, index+1, path, list) pathbytes := []byte(path)
pathbytes = append(pathbytes, str2[index])
process(str2, index+1, string(pathbytes), list)
} // 解法二的优化
func minCost3(s1 string, s2 string) int {
if len(s1) == 0 || len(s2) == 0 {
return len(s2)
}
M := len(s2)
N := len(s1)
dp := make([][]int, M)
for i := 0; i < M; i++ {
dp[i] = make([]int, N)
}
ans := M
for start := 0; start < N; start++ { // 开始的列数
if s2[0] != s1[start] {
dp[0][start] = M
}
for row := 1; row < M; row++ {
if s2[row] == s1[start] || dp[row-1][start] != M {
dp[row][start] = row
} else {
dp[row][start] = M
}
}
ans = getMin(ans, dp[M-1][start])
// 以上已经把start列,填好
// 以下要把dp[...][start+1....N-1]的信息填好
// start...end end - start +2
for end := start + 1; end < N && end-start < M; end++ {
// 0... first-1 行 不用管
first := end - start
if s2[first] == s1[end] && dp[first-1][end-1] == 0 { } else {
dp[first][end] = M
}
for row := first + 1; row < M; row++ {
dp[row][end] = M
if dp[row-1][end] != M {
dp[row][end] = dp[row-1][end] + 1
}
if dp[row-1][end-1] != M && s2[row] == s1[end] {
dp[row][end] = getMin(dp[row][end], dp[row-1][end-1])
}
}
ans = getMin(ans, dp[M-1][end])
}
}
return ans
} func getMin(a int, b int) int {
if a < b {
return a
} else {
return b
}
}

执行结果如下:

2021-06-11:给定两个字符串s1和s2,问s2最少删除多少字符可以成为s1的子串? 比如 s1 = “abcde“,s2 = “axbc“。的更多相关文章

  1. 给定两个字符串 s 和 t,它们只包含小写字母。 字符串 t 由字符串 s 随机重排,然后在随机位置添加一个字母。 请找出在 t 中被添加的字母。

    给定两个字符串 s 和 t,它们只包含小写字母.字符串 t 由字符串 s 随机重排,然后在随机位置添加一个字母.请找出在 t 中被添加的字母. 示例: 输入: s = "abcd" ...

  2. 给定两个字符串,均只包含英文字母,需区分大小写,一个是源字符串SS(长度<1000), 另一个是目标字符串TS(长度<1000),请问能否通过删除SS中的字符(不改变顺序)将它变换成TS,如果可以输出“YES",不可以则输出“NO"。 输入说明:第一行为源字符串SS,第二行为目标字符串TS。

    import java.util.Scanner;/*    给定两个字符串,均只包含英文字母,需区分大小写,一个是源字符串SS(长度<1000),    另一个是目标字符串TS(长度<1 ...

  3. [Swift]LeetCode712. 两个字符串的最小ASCII删除和 | Minimum ASCII Delete Sum for Two Strings

    Given two strings s1, s2, find the lowest ASCII sum of deleted characters to make two strings equal. ...

  4. 【leet-code】712. 两个字符串的最小ASCII删除和

    题目描述 给定两个字符串s1, s2,找到使两个字符串相等所需删除字符的ASCII值的最小和. 示例 1: 输入: s1 = "sea", s2 = "eat" ...

  5. poj 3415 后缀数组 两个字符串中长度不小于 k 的公共子串的个数

    Common Substrings Time Limit: 5000MS   Memory Limit: 65536K Total Submissions: 11469   Accepted: 379 ...

  6. Q712 两个字符串的最小ASCII删除和

    给定两个字符串s1, s2,找到使两个字符串相等所需删除字符的ASCII值的最小和. 示例 1: 输入: s1 = "sea", s2 = "eat" 输出: ...

  7. Python-求解两个字符串的最长公共子序列

    一.问题描述 给定两个字符串,求解这两个字符串的最长公共子序列(Longest Common Sequence).比如字符串1:BDCABA:字符串2:ABCBDAB.则这两个字符串的最长公共子序列长 ...

  8. Leetcode之动态规划(DP)专题-712. 两个字符串的最小ASCII删除和(Minimum ASCII Delete Sum for Two Strings)

    Leetcode之动态规划(DP)专题-712. 两个字符串的最小ASCII删除和(Minimum ASCII Delete Sum for Two Strings) 给定两个字符串s1, s2,找到 ...

  9. Java实现 LeetCode 712 两个字符串的最小ASCII删除和(最长公共子串&&ASCII值最小)

    712. 两个字符串的最小ASCII删除和 给定两个字符串s1, s2,找到使两个字符串相等所需删除字符的ASCII值的最小和. 示例 1: 输入: s1 = "sea", s2 ...

  10. ✡ leetcode 161. One Edit Distance 判断两个字符串是否是一步变换 --------- java

    Given two strings S and T, determine if they are both one edit distance apart. 给定两个字符串,判断他们是否是一步变换得到 ...

随机推荐

  1. DNS BIND之dnssec安全

    公司一大早域名解析出问题了,网抓项目都无法抓取到进销存数据. 查询后发现是运维周末重启了dns服务. 网上找到的解决方法: 在BIND的配置文件(/etc/named.conf)中打开DNSSEC选项 ...

  2. 基于对象的实时空间音频渲染丨Dev for Dev 专栏

    本文为「Dev for Dev 专栏」系列内容,作者为声网音频算法工程师 李嵩. 随着元宇宙概念的引入,空间音频这项技术慢慢映入大家的眼帘.关于空间音频的基础原理,我们做过一期科普视频 -- 「空间音 ...

  3. 程序员必须掌握的java进制转换(全网最详细讲解)

    前言 在上一篇文章中,壹哥给大家讲了Java里的各种运算符.其中在讲解位运算符时,我给大家提到了计算机中进制的概念.但是现在很多小白同学,对进制的概念还不够了解,比如二进制.八进制.十六进制都是怎么回 ...

  4. Spring Data Redis 框架

    系统性学习,移步IT-BLOG 一.简介 对于类似于首页这种每天都有大量的人访问,对数据库造成很大的压力,严重时可能导致瘫痪.解决方法:一种是数据缓存.一种是网页静态化.今天就讨论数据缓存的实现 Re ...

  5. TCC 分布式事务解决方案

    更多内容,前往 IT-BLOG 一.什么是 TCC事务 TCC 是Try.Confirm.Cancel三个词语的缩写,TCC要求每个分支事务实现三个操作:预处理Try.确认Confirm.撤销Canc ...

  6. Leetcode Practice -- 字符串

    目录 14. 最长公共前缀 思路解析 151. 反转字符串中的单词 思路解析 125. 验证回文串 思路解析 415. 字符串相加 思路解析 3. 无重复字符的最长子串 思路解析 8. 字符串转换整数 ...

  7. golang 中的 cronjob

    引言 最近做了一个需求,是定时任务相关的.以前定时任务都是通过 linux crontab 去实现的,现在服务上云(k8s)了,尝试了 k8s 的 CronJob,由于公司提供的是界面化工具,使用.查 ...

  8. 在Kubernetes(k8s)中部署 jenkins

    在Kubernetes(k8s)中部署 jenkins YAML配置文件 由于jenkins需要持久化存储,通过nfs动态供给pvc存储卷. 可以参考我之前的文档:https://cloud.tenc ...

  9. 利用NGINX搭建部署直播流媒体服务器

    直播如今是一个老生常谈的问题,怎么用于直播,大多数人只晓得,大佬某平台直播软件,点击开始即可直播.那么如何来搭建一个简易的直播平台呢?仅仅是有直播功能,没有涉及转码以及播放软件. 安装nginx以及r ...

  10. Sitecore10 Demo演示环境Azure一键部署(Step By Step Guide to installing Sitecore10 in Azure Paas)

    本文演示Sitecore XP Single(XP0)在Azure上的一键部署,即"30分钟生成Sitecore演示环境"的一环. 关于XP(即Sitecore Experienc ...