【lc刷题】647 回文子串(DP)

    xiaoxiao2022-07-06  189

    45/300

    回文子串 给定一个字符串,你的任务是计算这个字符串中有多少个回文子串。   具有不同开始位置或结束位置的子串,即使是由相同的字符组成,也会被计为是不同的子串。   示例 1:   输入: “abc” 输出: 3 解释: 三个回文子串: “a”, “b”, “c”.   示例 2:   输入: “aaa” 输出: 6 说明: 6个回文子串: “a”, “a”, “a”, “aa”, “aa”, “aaa”. 注意:   输入的字符串长度不会超过1000。

    动态规划类型,第三道: 举例X属于未知数字。 ‘aXXb’肯定不是回文,如果是 ‘aXXa’ 呢? 需要判断中间两位是不是回文,如果这个状态True/False已经被记录,可以直接调取。 同理,'aXb’肯定不是回文,‘aXa’ 则需调取X的状态。 再小一点‘ab’,‘aa’我们可以直接判断True or False。 最小到‘a’,‘b’直接记录True

    我们把思路从底往上实现: ‘abca’

    0 1 2 3 [ a, b, c, a], 0 [a, T, F, F, F], 1 [b, , T, F, F], 2 [c, , , T, F], 3 [a, , , , T] class Solution: def countSubstrings(self, s): """ :type s: str :rtype: int """ if not s: return 0 n = len(s) #n*n的小本本准备好 memo = [[None]*n for _ in range(n)] count = 0 #遇True则+1 #记录'a','b' = True for i in range(n): memo[i][i] = True count += 1 for j in range(1,n): for i in range(j): # 'abcd' # j = 1, i = 0 [0][1]ab # j = 2, i = 0, 1 [0][2]ac [1][2]bc # j = 3, i = 0, 1, 2 [0][3]abcd [1][3]bcd [2][3]cd #'aa' 'aXa' if s[i] == s[j] and j-i <= 2: memo[i][j] = True count += 1 #'aXXa' 'aXXXa' elif s[i] == s[j] and j-i > 2: #调取状态 if memo[i+1][j-1]: memo[i][j] = True count += 1 else: memo[i][j] = False #'ab''aXb''aXXb'.. else: memo[i][j] = False return count

    但,从大佬处发现了更高效的办法!

    画个思路丑图:‘abcded’

    class Solution: def countSubstrings(self, s): """ :type s: str :rtype: int """ if not s: return 0 n = len(s) count = 0 for i in range(2*n-1): l = i//2;r = (i+1)//2 while l >= 0 and r < n and s[l] == s[r]: count += 1 l -= 1; r += 1 return count

    最新回复(0)