为什么即使使用备忘录也能获得TLE?

问题描述

这是问题陈述

给出两个字符串s1和s2,返回它们最长的公共子序列的长度。

字符串的子序列是从原始字符串生成的新字符串,其中删除了一些字符(可以是一个字符),而不会更改其余字符的相对顺序。 (例如,“ ace”是“ abcde”的子序列,而“ aec”则不是)。两个字符串的共同子序列是两个字符串共同的子序列。

如果没有公共子序列,则返回0。

这是我的代码

class Solution {
public:
    int dp[1001][1001];
    int lcs(string s1,string s2,int n,int m){
        if (n==0 || m == 0)
            return 0;
        if(dp[n][m]!=-1)
            return dp[n][m];
        if (s1[n-1] == s2[m-1])
        {
            return dp[n][m]=  1 + lcs(s1,s2,n-1,m-1);
        }
        else
        {
            return dp[n][m]= max(lcs(s1,m),lcs(s1,n,m-1));
        }
        return dp[n][m];
    }
    int longestCommonSubsequence(string s1,string s2) {
        memset(dp,-1,1001*1001*sizeof(int));
        return lcs(s1,s1.size(),s2.size());
        
    }
};

谢谢

解决方法

在函数定义中使用按引用调用,而不是按值调用。

int lcs(string &s1,string &s2,int n,int m);
int longestCommonSubsequence(string &s1,string &s2);
,

您的实施至少可以进行2项进一步的改进。

  • 您正在使用递归算法,将其重写为迭代版本
  • 您使用的是1001 * 1001数组,因此您将缓存浪费了一些时间

存在一种更加节省空间的算法Hirschberg's algorithm,用于仅返回LCS的长度。