一次编辑
1.题目要求
字符串有三种编辑操作:插入一个英文字符、删除一个英文字符或者替换一个英文字符。
给定两个字符串,编写一个函数判定它们是否只需要一次(或者零次)编辑。
示例1:
输入:
first = "pale"
second = "ple"
输出: True
示例2
输入:
first = "pales"
second = "pal"
输出: False
2.解题思路
通过字符串长度之差的绝对值判断是否符合题目要求
1,绝对值差值 > 1,则为不符合条件的字符串。
2,绝对值差值 = 1,该字符串通过插入、删除操作可实现一次操作。
找到字符串长度最大的字符串,轮流删除最大字符串的每个字符后,
再与另一个字符串进行比较,只要相等就是符合条件的字符串。
3,绝对值差值 = 0,该字符串通过替换操作可实现一次操作。
当 相同下标字符不相等的数量 > 1 时,则为不符合条件的字符串。
3.代码实现
class Solution {
public boolean oneEditAway(String first, String second) {
int dif = first.length() - second.length();
//取绝对值
// int k = Math.abs( dif );
int t = ( dif < 0 ) ? -dif : dif;
char[] ch3 = ( dif < 0 ) ? second.toCharArray() : first.toCharArray();
char[] ch1 = first.toCharArray();
char[] ch2 = second.toCharArray();
//不符合
if( t > 1 ){
return false;
}
//插入,删除
if( t == 1 ){
char[] max = new char[first.length()];
char[] min = new char[first.length()];
if( dif < 0 ){
max = ch2;
min = ch1;
}else{
max = ch1;
min = ch2;
}
for( int i = 0; i < ch3.length; i++ ){
for( int j = 0; j < max.length-i-1; j++ ){
max[j+i]=max[i+j+1];
}
max[max.length-1] = ' ';
System.out.println( String.valueOf(max).trim()+"="+ String.valueOf(min) );
if( String.valueOf(max).trim().equals( String.valueOf(min) ) ){
return true;
}
if( dif < 0 ){
max = second.toCharArray();
}else{
max = first.toCharArray();
}
System.out.println( String.valueOf(max)+"===" );
}
return false;
}
//替换
if( t == 0 ){
int flag = 0;
//字符串长度相等
for( int i = 0; i < first.length(); i++ ){
// System.out.println(f);
if( ch1[i]!=ch2[i] ){
flag++;
}
if( flag > 1 ){
return false;
}
}
return true;
}
return false;
}
}
4.最优解法
双指针模拟
为了方便,我们令 a = first、b = second,两者长度为 n 和 m,并让 a 为两者中的长度较短的那个(若 b 较短,则将两者交换)。
接下来是简单的双指针处理(使用 cnt 记录操作次数):
我们最多使用不超过一次的操作,因此如果 ∣n−m∣>1,直接返回 False;
若两者长度差不超过 1,使用 i 和 j 分别指向两字符的最左侧进行诸位检查:
若 a[i]=b[j],让 i 和 j 继续后移进行检查;
若 a[i] != b[j],根据两字符串长度进行分情况讨论:
若 n = m,说明此时只能通过「替换」操作消除不同,分别让 i 和 j 后移,并对 cnt 进行加一操作;
若 n != m,由于我们人为确保了 a 更短,即此时是 n < m,此时只能通过对 a 字符串进行「添加」操作来消除不同,此时让 j 后移,i 不动(含义为在 a 字符串中的 i 位置增加一个 b[j] 字符),并对 cnt 进行加一操作。
最终我们根据 cnt 是否不超过 1 来返回结果。
时间复杂度:令 n 和 m 分别为两字符串长度,复杂度为 O(max(n,m))
空间复杂度:O(1)
作者:AC_OIer
class Solution {
public boolean oneEditAway(String a, String b) {
int n = a.length(), m = b.length();
if (Math.abs(n - m) > 1) return false;
if (n > m) return oneEditAway(b, a);
int i = 0, j = 0, cnt = 0;
while (i < n && j < m && cnt <= 1) {
char c1 = a.charAt(i), c2 = b.charAt(j);
if (c1 == c2) {
i++; j++;
} else {
if (n == m) {
i++; j++; cnt++;
} else {
j++; cnt++;
}
}
}
return cnt <= 1;
}
}