##題目 給定一個字符串 s,找到 s 中最長的迴文子串。你能夠假設 s 長度最長爲1000。java
示例:bash
輸入: "babad"
輸出: "bab"
注意: "aba"也是有效答案
複製代碼
示例:學習
輸入: "cbbd"
輸出: "bb"
複製代碼
一開始是想用最笨的方法來解的,也就是找出全部的字串,而後再對全部的子串進行迴文檢測,並記錄長度。這種方式時間複雜度可想而知,O(n)*O(n)*O(n)=O(n^3)。因此這種確定是不能知足咱們要求的。spa
ok,那咱們來分析一下這個問題,先把這個問題特殊化;code
假如輸入的字符串長度就是1索引
那麼這個字符串的最長迴文串就是它本身,長度就是1字符串
假如字符串長度爲2,它要是迴文串的化,就須要兩個字符是相等的。string
即:s[i] == s[j] 且i-j=1(此處假定i是較大索引位置)it
那麼對於i-j>1的狀況下呢?是否是隻要知足下面的條件就能夠了:io
即:s[i] == s[j]&&s[i-1] == s[j+1]
其實這種思路就是動態規劃。關於動態規劃的理論性文字就不碼了,有興趣的小夥伴闊以自行學習。下面就針對這個問題碼一下代碼:
public String longestPalindrome(String s) {
// 長度爲1,返回當前串
if (s.length()==1){
return s;
}
//長度爲2而且兩個字符相等則返回
if (s.length()==2&&s.charAt(0)==s.charAt(1)){
return s;
}
//用於標記isLongestPalindrome[j][i]即從j到i是不是迴文串;
//如isLongestPalindrome[1][5]==true則表示字符串索引位置從1到5的子串是迴文串。
boolean[][] isLongestPalindrome = new boolean[s.length()][s.length()];
//最長迴文串初始最大爲0
int maxlen = 0;
//對應的maxlen的開始索引位置
int beginIndex = 0;
//對應的maxlen的結束索引位置
int lastIndex = 0;
for (int i=0;i<s.length();i++){
int j=i;
while(j>=0){
//知足上述的第三個條件,即當前s.charAt(i)==s.charAt(j)並
//且s[j+1到i-1]也是迴文串
if (s.charAt(i)==s.charAt(j)&&(i-j<2||isLongestPalindrome[j+1][i-1])){
isLongestPalindrome[j][i]=true;
if (maxlen < i-j+1) {
beginIndex = j;
lastIndex = i+1;
maxlen = i-j+1;
}
}
j--;
}
}
return s.substring(beginIndex,lastIndex);
}
複製代碼