题目描述
给定一个非空字符串 s,最多删除一个字符。判断是否能成为回文字符串。
示例 1:
输入: s = "aba"
输出: true
示例 2:
输入: s = "abca"
输出: true
解释: 你可以删除c字符。
示例 3:
输入: s = "abc"
输出: false'
解题思路
本题可以使用双指针的方式来解决。定义两个指针 left 和 right,分别指向字符串的首尾字符。比较这两个字符,如果相等,则将指针向中间移动,并继续比较下一对字符;如果不相等,则有两种情况:
- 删除左指针指向的字符,即判断去掉左指针后剩余部分是否是回文字符串。
- 删除右指针指向的字符,即判断去掉右指针后剩余部分是否是回文字符串。
如果以上两种情况中任意一种情况成立,即可判断原字符串通过最多删除一个字符能够变成回文字符串。
代码实现
function validPalindrome(s: string): boolean {
let left = 0;
let right = s.length - 1;
while (left < right) {
if (s[left] !== s[right]) {
return isPalindrome(s, left + 1, right) || isPalindrome(s, left, right - 1);
}
left++;
right--;
}
return true;
}
function isPalindrome(s: string, left: number, right: number): boolean {
while (left < right) {
if (s[left] !== s[right]) {
return false;
}
left++;
right--;
}
return true;
}
复杂度分析
- 时间复杂度:O(n),其中 n 是字符串 s 的长度。双指针遍历整个字符串的时间复杂度是 O(n),判断子字符串是否是回文字符串的时间复杂度也是 O(n)。
- 空间复杂度:O(1)。只使用了常数空间。