问题
求一个字符串的最长回文子串
Input: "babad"
Output: "bab"
Note: "aba" is also a valid answer.
思路
这道题跟647. Palindromic Substrings差不多,一个是求子回文串数量,一个是求最长子回文串。
只要把Palindromic Substrings的代码改写一下,把求数量改成求最长就可以了。
主要用了两种方法,一个是朴素的做法,按每个字符从两边扩张,另一个是著名的马拉车算法。具体思路在Palindromic Substrings中已经分析过了,此处不多阐述。
代码
朴素做法:时间复杂度O(n^2),空间复杂度O(1)
class Solution(object):
def longestPalindrome(self, s):
"""
:type s: str
:rtype: int
"""
n = len(s)
maxI = 0
maxLen = 0
for i in range(2*n-1):
left = i/2
right = left + i%2
while(left >= 0 and right < n and s[left]==s[right] ):
left -= 1
right += 1
if(right - left -1 > maxLen):
maxI = left + 1
maxLen = right - left -1
return s[maxI:maxI+maxLen]
马拉车算法:时间复杂度O(n),空间复杂度O(1)
class Solution(object):
def longestPalindrome(self, s):
"""
:type s: str
:rtype: int
"""
s = '#' + '#'.join(s) + '#'
n = len(s)
p = [0]*n
id = mx = 0
maxR = 0
maxI = 0
for i in range(1,n-1):
if(mx > i):
p[i] = min(mx-i, p[2*id-i])
while i+p[i]+1 < n and i-p[i]-1 >=0 and s[i+p[i]+1] == s[i-p[i]-1]:
p[i] += 1
if(i + p[i] > mx):
id = i
mx = i + p[i]
if(p[i]>maxR ):
maxR = p[i]
maxI = i
return s[maxI - maxR + 1: maxI + maxR].replace('#','')