647. 回文子串

动态规划

class Solution {
    public int countSubstrings(String s) {

        /**
         * dp[i][j]定义为区间为[i, j]的子串是否是回文串
         */
        boolean[][] dp = new boolean[s.length()][s.length()];
        int count = 0;

        /**
         * 因为需要判断dp[i + 1][j - 1]是否也是回文串,因此需要i从大到小遍历
         */
        for (int i = s.length() - 1; i >= 0; i--) {

            for (int j = i; j < s.length(); j++) {

                /**
                 * 如果i和j的字符相等,且i和j是同一个字符或者是相邻字符,或者i往右缩一步,j往左缩一步得到的字符串也是回文串
                 * 就可以确定[i, j]区间也是回文串
                 */
                if (s.charAt(i) == s.charAt(j) && (j - i <= 2 || dp[i + 1][j - 1])){

                    count++;
                    dp[i][j] = true;
                }
            }
        }

        return count;
    }
}

/**
 * 时间复杂度 O(n^2)
 * 空间复杂度 O(n^2)
 */

暴力解法

class Solution {
    public int countSubstrings(String s) {

        /**
         * 三层循环
         * 对于每个字符本身都是回文串,因此初始数量为字符串长度
         * 对于每个字符i,用一个从0开始的指针j一次遍历,只要[j, i]区间内的子串是回文串,总数就加1
         */
        int count = s.length();

        for (int i = 0; i < s.length(); i++) {

            for (int j = 0; j < i; j++) {

                if (isValid(s.substring(j, i + 1))){
                    count++;
                }
            }
        }

        return count;
    }

    /**
     * 判断回文串
     */
    public boolean isValid(String s){

        int left = 0;
        int right = s.length() - 1;

        while (left < right){

            if (s.charAt(left) == s.charAt(right)){

                left++;
                right--;
            }
            else {
                return false;
            }
        }

        return true;
    }
}

/**
 * 时间复杂度 O(n^3)
 * 空间复杂度 O(1)
 */

https://leetcode-cn.com/problems/palindromic-substrings/

posted @ 2022-03-01 13:02  振袖秋枫问红叶  阅读(30)  评论(0)    收藏  举报