1. 程式人生 > >LetCode: 5. 最長迴文子串

LetCode: 5. 最長迴文子串

提示

LintCode中的相關演算法題實現程式碼,可以在我的GithHub中下載。

題目需求

給定一個字串 s,找到 s 中最長的迴文子串。你可以假設 的最大長度為1000。

示例 1:

輸入: "babad"
輸出: "bab"
注意: "aba"也是一個有效答案。

示例 2:

輸入: "cbbd"
輸出: "bb"

 

解題思路

1.思想:

     1)將子串分為單核和雙核的情況,單核即指子串長度為奇數,雙核則為偶數;

    2)遍歷每個除最後一個位置的字元index(字元位置),單核:初始low = 初始high = index,low和high均不超過原字串的下限和上限;判斷low和high處的字元是否相等,相等則low++、high++(雙核:初始high = 初始low+1 = index + 1);

    3)每次low與high處的字元相等時,都將當前最長的迴文子串長度與high-low+1比較。後者大時,將最長的迴文子串改為low與high之間的;

    4)重複執行2)、3),直至high-low+1 等於原字串長度或者遍歷到最後一個字元,取當前擷取到的迴文子串,該子串即為最長的迴文子串。

2.時間複雜度解釋:

   遍歷字元:一層迴圈、O(n-1);

   找以當前字元為中心的最長迴文子串:巢狀兩個獨立迴圈、O(2n*(n-1)) = O(n^2)。

實現程式碼

class Solution {
      
     public String longestPalindrome(String s) {
        if(s.length()==0)
            return "";
       int start=0, end=0;
        for (int i = 0; i <s.length(); i++) {
            int i1 = expandAroundCenter(s, i, i);
            int i2 = expandAroundCenter(s, i, i + 1);
            int length= Math.max(i1,i2);
            if(length>end-start){
                start=i-(length-1)/2;
                end=i+length/2;
            }
        }
        return s.substring(start,end+1);
    }

   private int expandAroundCenter(String s, int i, int j){
        int left=i,right=j;
        while (left>=0 && right<s.length() && s.charAt(left) == s.charAt(right)){
            left--;
            right++;
        }
        return right-left-1;
   }
}