Leecode 680 验证回文串 II 双指针法

简介: 第一次报错是因为没有判断删除一个字符后的情况第二次报错是因为没有添加是删除一个字符而不是删除多个字符能不能构成回文串的条件第三次报错是因为没有考虑先删除左边还是右边的问题,有些奇葩它先删除左边不可以通过,得先删除右边

题目

做这道题可谓是一波三折😢


第一次报错是因为没有判断删除一个字符后的情况

第二次报错是因为没有添加是删除一个字符而不是删除多个字符能不能构成回文串的条件

第三次报错是因为没有考虑先删除左边还是右边的问题,有些奇葩它先删除左边不可以通过,得先删除右边

第四次报错是因为没有添加如果先删除左边就可以通过的话就不用判断删除右边的情况,导致比如’acba‘原本可以通过测试,但右边删除又返回false,造孽啊~

image.pngimage.png


思路

将字符串转为字符数组 a[ ]

回文数的判断的实现:借助双指针 i 和 j - 如果字符匹配(a[i]==a[j])就继续向中间逼近(i++ , j–),如果字符不匹配 (a[i]!=a[j] ) 就考虑删除一个字符。

如何保证是删除一个字符而不是多个,定义变量num=0;每 ‘删除’ 一个字符num++,如果遇到字符不匹配那就先判断num是否=1,如果=1,说明已经删除过一个字符了,直接返回false;

删除一个单词的实现:当左右指针指向的字符不匹配时,先考虑删除左边的字符(即i++)

如果删除左边的字符后任然不是回文串,那就将 ‘删除’ 的字符复原,删除次数复原(即i–,num–),再试试删除右边的字符(即j–),如果还不是回文串,那就返回false

特例的处理:如果是一个长度的字符串(即字符),直接返回 true

代码

class Solution {
    public boolean validPalindrome(String s) {
        char[] c = s.toCharArray();
        int i=0,j=c.length-1;
        char word1=c[i];
        char word2=c[j];
        int num=0;//判断删除了几个单词,如果超过了两个单词就返回false
        //判断是不是回文串
        if(c.length==1){
            return true;
        }
        boolean loop=true;
        while(i<j ){
            word1=c[i];
            word2=c[j];
            //还包括先删除左边的单词还是右边的单词的情况
            if(word1!=word2){
                if(num==1){
                    loop=false;
                    break;
                }
                i++;
                word1=c[i];
                if(word1==word2){
                    num++;
                    i++;
                    j--;
                    continue;
                }
                //复原word1
                i--;
                word1=c[i];
                //更新a[j]
                j--;
                word2=c[j];
                if(word1==word2){
                    num++;
                    i++;
                    j--;
                    continue;
                }
                loop=false;
                break;
            }
            i++;
            j--;
            loop=true;
        }
        //如果loop为false的话才判断先删除右边的情况
        //先删除右边再删除左边的情况
        //充值i,j,loop,num
        if(loop){
            return loop;
        }
        loop=true;
        num=0;
        i=0;
        j=c.length-1;
        while(i<j ){
            word1=c[i];
            word2=c[j];
            //还包括先删除左边的单词还是右边的单词的情况
            if(word1!=word2){
                if(num==1){
                    loop=false;
                    break;
                }
                j--;
                word2=c[j];
                if(word1==word2){
                    num++;
                    i++;
                    j--;
                    continue;
                }
                //复原word2
                j++;
                word2=c[j];
                //更新a[i]
                i++;
                word1=c[i];
                if(word1==word2){
                    num++;
                    i++;
                    j--;
                    continue;
                }
                loop=false;
                break;
            }
            i++;
            j--;
            loop=true;
        }
        return loop;
    }
}
相关文章
|
4月前
代码随想录 Day46 动态规划14 LeetCode T392 判断子序列 T115 不同的子序列
代码随想录 Day46 动态规划14 LeetCode T392 判断子序列 T115 不同的子序列
39 0
|
5月前
【每日一题Day175】LC1147段式回文 | 贪心 +双指针
【每日一题Day175】LC1147段式回文 | 贪心 +双指针
23 0
|
3月前
|
测试技术 Perl
【动态规划】【记忆化搜索】【回文】1312让字符串成为回文串的最少插入次数
【动态规划】【记忆化搜索】【回文】1312让字符串成为回文串的最少插入次数
|
25天前
|
算法
代码随想录算法训练营第五十六天 | LeetCode 647. 回文子串、516. 最长回文子序列、动态规划总结
代码随想录算法训练营第五十六天 | LeetCode 647. 回文子串、516. 最长回文子序列、动态规划总结
34 1
|
4月前
|
JavaScript
代码随想录 Day48 动态规划16 T647 回文子串 T516最长回文子序列
代码随想录 Day48 动态规划16 T647 回文子串 T516最长回文子序列
29 0
|
11月前
Leecode 5. 最长回文子串
Leecode 5. 最长回文子串
29 1
|
11月前
[leetcode] 522. 最长特殊序列 II 暴力 + 双指针
[leetcode] 522. 最长特殊序列 II 暴力 + 双指针
73 0
|
12月前
|
算法 Java
判断回文串(hdu 2029)双指针法
题目来自 hdu 杭州电子科技大学的一个算法网站
LeetCode 680.验证回文字符串 Ⅱ(双指针法)
LeetCode 680.验证回文字符串 Ⅱ(双指针法)
65 0
LeetCode 680.验证回文字符串 Ⅱ(双指针法)
|
Java C++
蓝桥杯-01子串(暴力)
蓝桥杯-01子串(暴力)