算法: 最长回文子串 二层动态规划

 

这是leetcode上的一道算法题python

对的就是这道题,,困扰了我整整一上午,,   一直也没考虑用动态规划作,,  最终用动态规划把他解决了!算法

回文串: 正过来和倒过来长的同样, 好比 理总理, 席主席。。。数组

思想是这样的:spa

  用 dp[i][j] 表示 字符串s的子串s[i:j] 是否是回文串  0表示不是  1表示是code

  当 i == j 的时候   dp[i][j] 都是1    blog

    (意思是s[1:1] s[2:2] 就是一个字符, 字符本身算是个回文子串)leetcode

  当 i == j-1 的时候,若是 s[i] == s[j]   那dp[i][j] =1    不然为0   字符串

    (俩字符,这俩是同样的就是回文字符  不然就不是)io

  其余状况,当 i < j-1 的时候, class

      若是 dp[i+1][j-1]==1 而且 s[i] == s[j] 的时候 dp[i][i] 就是1 

        (s[j] 和 s[j] 中间 不包含他俩,原来就是回文的,  他俩仍是一个字符,, 那算上这俩也是回文)

      不然  dp[i][j] 都是0

         (1 s[i]和s[j]中间不包含他俩, 原来不是回文,,那算上他俩也不是回文。

          2 若是他俩中间原本是回文 他俩不是一个字符,那算上他俩以后就不是回文)

 

这样的方式 初始化二维数组, 先把对角线填充上, 而后再把 对角线上一层(两个相邻元素是否相等) 填充上, 

而后斜着一层一层填充表就能够。

为了不从新查表获得最长子串,  能够在填充过程,记录当前最长的子串长度,起始index和结束index

 

把个人草纸拍下来,你们别嫌弃丑, 填表顺序记录下来 但愿对你们有帮助:

  

 

 

个人python代码:

 1 class Solution:  2 def longestPalindrome(self, s):  3 """  4  :type s: str  5  :rtype: str  6 """  7 length = len(s) # 字符串长度  8 max_length = 1 # 动态规划过程当中记录最长回文串长度 默认1是一个字符的状况  9 start = 0 # 最长回文子串的开始位置 默认一开始s[0]本身是一个回文子串 10 end = 0 # 回文子串的阶数位置 11 # 初始化一个 s长度的二维数组 记录dp过程 12 record = [[0 for i in range(length)] for _ in range(length)] 13 # record[i][j] 表明 s[i:j] 是否是回文子串 14 for i in range(length): 15 # 对角线全填充1 表明 一个字符是回文子串 16 record[i][i] = 1 17 # 相邻两个字符若是相同 就记录1 不然记录0 18 if i >= 1: 19 if s[i] == s[i-1]: 20 record[i-1][i] = 1 21 max_length = 2 22 start = i-1 23 end = i 24 else: 25 record[i-1][i] = 0 26 # 前面两步骤把i j 相差0 和相差1 的状况都在表里填充上了 27 # 下面 改用left看成起始位置 right看成结束位置i和j 28 # 用i表明left和start的间隔 从2开始到length-1为止 29 # 用j从1到length-i 30 # 下面开始填充斜对角线 31 for i in range(2, length): 32 for j in range(length - i): 33 left = j 34 right = j + i 35 # 若是 s[left+1: right-1] 是回文串 而且 这两个位置字符相同 则s[left:right]也是回文的 不然不是 36 if record[left+1][right-1] == 1 and s[left] == s[right]: 37 record[left][right] = 1 38 # 若是发现当前回文串比以前发现的长度长 则更新长度 开始位置和结束位置 39 if right - left + 1 > max_length: 40 start = left 41 end = right 42 max_length = right - left + 1 43 else: 44 record[left][right] = 0 45 # 返回发现的最长回文串 46 return s[start: end+1] 47 48 49 if __name__ == '__main__': 50 s = Solution() 51 res = s.longestPalindrome("abbajlhkh") 52 print(res)
相关文章
相关标签/搜索