【LeetCode】Longest Palindromic Substring 解題報告
阿新 • • 發佈:2019-01-03
DP、KMP什麼的都太高大上了,自己想了個樸素的遍歷方法。
【題目】
Given a string S,
find the longest palindromic substring in S.
You may assume that the maximum length of S is
1000, and there exists one unique longest palindromic substring.
【思路】(應該算是O(n)吧)
從中間向兩端搜尋,分別找到以每個字母為中心的最長迴文子串,如果兩邊剩餘的元素已經比當前最長迴文子串的一半還短時,停止遍歷。
大家別看程式碼長,是為了便於理解的。
【Java程式碼】
public class Solution { public String longestPalindrome(String s) { int len = s.length(); if (s == null || len == 1){ return s; } String ret = ""; int mid = len / 2; int i = 0; while (true) { //遍歷到s兩端時,如果以mid+i或mid-i為中心的最長迴文都不比當前最優解長,遍歷結束 if (2*(len-(mid+i)) < ret.length() && 2*(mid-i+1) < ret.length()) { break; } String str1 = palindrome1(s, mid+i); String str2 = palindrome2(s, mid+i); String str3 = palindrome1(s, mid-i); String str4 = palindrome2(s, mid-i); if (str1.length() > ret.length()) { ret = str1; } if (str2.length() > ret.length()) { ret = str2; } if (str3.length() > ret.length()) { ret = str3; } if (str4.length() > ret.length()) { ret = str4; } i++; } return ret; } //找出s中以index為中心的aba型的迴文子串 public String palindrome1(String s, int index) { String ret = ""; int i = index, j = index; while (i>=0 && j<s.length()) { if (s.charAt(i) != s.charAt(j)) { break; } ret = s.substring(i, j+1); i--; j++; } return ret; } //找出s中以index和index+1為中心的abba型迴文子串 public String palindrome2(String s, int index) { String ret = ""; int i = index, j = index+1; while (i>=0 && j<s.length()) { if (s.charAt(i) != s.charAt(j)) { break; } ret = s.substring(i, j+1); i--; j++; } return ret; } }
【分析】
後來在網上找了類似的解法。如 http://leetcode.com/2011/11/longest-palindromic-substring-part-ii.html ,為了不用區分aba型和abba型的迴文子串,構造了一個新的字串 t ,在兩端和每兩個字母之間插入一個特殊字元 ‘#’ ,這樣當以‘#’為中心的迴文子串就是我的程式碼中abba型子串。
我的程式碼與之相比還使用了一個小trick,即從中間向兩端遍歷,這樣如果中間已經有比較長的迴文子串了,那麼兩端比較偏的迴文子序列就可省去判斷。
一遍就AC了,後來比較了網上的解法,不禁為自己有點小激動呢~。
分析可能有誤,也許只是自我感覺良好,歡迎大家指正!