LeetCode 1278. 分割回文串 III (二维线性DP、DP预处理)

分割回文串 III

  • 思路:
    这种分割字符串的题目往往都是这样设计DP的阶段的:考虑前缀 [ 0 , i ] [0,i] [0,i]分割成 k k k段的花费。
  • DP 方程: d p [ k ] [ i ] = m i n ( d p [ k − 1 ] [ j ] + c o s t [ j + 1 , i ] ) ( j < i ) dp[k][i]=min(dp[k-1][j]+cost[j+1,i]) (jdp[k][i]=min(dp[k1][j]+cost[j+1,i])(j<i)

考虑在 c o s t [ l , r ] cost[l,r] cost[l,r]可以预处理出。
时间复杂度: O ( n 3 ) O(n^3) O(n3)

/*  
    dp[k][i] = min(dp[k][i],dp[k-1][j]+cost[j+1,i]);
*/
class Solution {
     
public:
    int dp[110][110],cost[110][110] = {
     0};
    int palindromePartition(string s, int K) {
     
        memset(dp,0x3f,sizeof(dp));
        int n = s.size();
        for(int i=0;i<n;i++)
            for(int j=i+1;j<n;j++)
                cost[i][j] = get_cost(s,i,j);

        for(int i=0;i<n;i++)
            dp[1][i] = cost[0][i];

        for(int k=2;k<=K;k++)
            for(int i=k-1;i<n;i++)
                for(int j=k-2;j<i;j++)
                    dp[k][i]= min(dp[k][i],dp[k-1][j]+cost[j+1][i]);

        return dp[K][n-1];
    }

    int get_cost(const string& s,int l,int r){
     
        int res = 0, i = l, j = r;
        while(i<j){
     
            if(s[i]!=s[j]){
     
                res++;
            }
            i++;
            j--;            
        }
        return res;
    }
};

  • 优化:
    • 空间上,可以用滚动数组去优化 d p [ ] [ ] dp[][] dp[][]到一维。
    • 时间上, c o s t [ i ] [ j ] cost[i][j] cost[i][j]也可以使用dp进行优化。
      c o s t [ l ] [ r ] = c o s r [ l + 1 ] [ r − 1 ] + ( s [ l ] ! = s [ r ] ) cost[l][r] = cosr[l+1][r-1]+(s[l]!=s[r]) cost[l][r]=cosr[l+1][r1]+(s[l]!=s[r])

你可能感兴趣的:(LeetCode,#,LC动态规划)