渣渣的Leetcode之旅(Python3)_5.最长回文子串(中等)
给你一个字符串 s,找到 s 中最长的回文子串。
示例 1:
输入:s = “babad”
输出:“bab”
解释:“aba” 同样是符合题意的答案。示例 2:
输入:s = “cbbd” 输出:“bb”
示例 3:
输入:s = “a” 输出:“a”
示例 4:
输入:s = “ac” 输出:“a”
提示:
1 <= s.length <= 1000
s 仅由数字和英文字母(大写和/或小写)组成
来源:力扣(LeetCode)
链接:https://leetcode-cn.com/problems/longest-palindromic-substring
著作权归领扣网络所有。商业转载请联系官方授权,非商业转载请注明出处。
首先最基础的想法是暴力,找出所有的字串然后判断是不是回文,但这样时间耗费很大。
然后进一步的想法是动态规划,如下:
长度为4,只要最中间的两个位置是回文,首位和末位的字符相等,那么这个4位子串就是回文
长度为5,只要最中间的三个位置是回文,首位和末位的字符相等,那么这个5位子串就是回文
长度为6,只要最中间的四个位置是回文,首位和末位的字符相等,那么这个6位子串就是回文
依此类推。。。
由此我们可以找出所有子串中的回文串,然后将结果保存在二位数组中,但这样遇到极长的串时会超时
class Solution:
def longestPalindrome(self, s: str) -> str:
if len(s) == 0 or len(s) == 1:
return s
array = [[0]*len(s) for i in range(len(s))]
num = 0
for i in range(2,len(s)+1):
for j in range(len(s)-1):
if i+j > len(s):
break
if i == 2:
if s[j] == s[j+1]:
array[j][j+1] = 1
num = 2
continue
if i == 3:
if s[j] == s[j+2]:
array[j][j+2] = 1
num = 3
continue
if s[j] == s[i+j-1] and array[j+1][i+j-2] == 1:
array[j][i+j-1] = 1
if num < i:
num = i
str_a = ""
if num == 0:
str_a = str_a + s[0]
return str_a
else:
fin = 0
for i in range(len(s)+100):
if array[i][i+num-1] == 1:
fin = i
break
for i in range(fin,fin+num):
str_a = str_a + s[i]
return str_a
优化一下:
由最基础的长度为2以及长度为3的回文串向外扩展
如果得到的长度为4或者为5的子串也是回文串,那就继续向外扩展至长度为6或者7,不断重复,直到不为回文串为止
如果得到的长度为4或者为5的子串不是回文串,那就找到下一组长度为2或者3的回文串向外扩展
通过向外扩展找回文串的方法,找到长度最长的回文串,输出即可
class Solution:
def longestPalindrome(self, s: str) -> str:
if len(s) == 0 or len(s) == 1:
return s
array = [[0]*len(s) for i in range(len(s))]
num = 0
fin_sta = 0
sta = 0
middle_num = 0
three_num = 0
for i in range(2,4): #这两个for循环用来找到所有长度为2和3的回文子串
for j in range(len(s)-1):
if i+j > len(s):
break
if s[j] == s[j+i-1]:
array[j][j+i-1] = 1
num = i
continue
for i in range(len(s)-2):
middle_num = 2
three_num = 3
if array[i][i+1] == 1:
low = i
high = i + 1
while True:
low = low - 1
high = high + 1
if low <0 or high > len(s)-1 or s[low] != s[high]:
break
if s[low] == s[high]:
middle_num += 2
sta = low
if num < middle_num:
num = middle_num
fin_sta = sta
if array[i][i+2] == 1:
low = i
high = i + 2
while True:
low = low - 1
high = high + 1
if low < 0 or high > len(s)-1 or s[low] != s[high]:
break
if s[low] == s[high]:
three_num += 2
sta = low
if num < three_num:
num = three_num
fin_sta = sta
str_a = ""
if num == 0:
str_a = str_a + s[0]