首页 > 搜索 > 动态规划算法的逆序方程,算法初步:再讨论一点动态规划

动态规划算法的逆序方程,算法初步:再讨论一点动态规划

互联网 2020-10-30 02:53:14
在线算命,八字测算命理

原创 by zoe.zhang

动态规划真的很好用啊,但是需要练习,还有很多技巧要学习。

1.滚动数组

动态规划是用空间换取时间,所以通常需要为DP数组开辟很大的内存空间来存放数据,但有的时候空间太大超过内存限制,特别是在OJ的时候,容易出现MLE的问题。而在一些动规的题目中,我们可以利用滚动数组来优化空间。

适用条件:DP状态转移方程中,仅仅需要前面若干个状态,而每一次转移后,都有若干个状态不会再被用到,也就是废弃掉,此时可以使用滚动数组来减少空间消耗。

优点:节约空间。

缺点:在时间消耗上没什么优势,有可能还带来时间上的额外消耗。在打印方案或者需要输出每一步的状态的时候比较困难,因为此时只有一个最终的状态结果。

举例:

1)一维数组:斐波那契数列

// 至少100个内存空间int d[100] = { 0 };d[0] = 1; d[1] = 1;for (int i = 2; i < 100; i++)d[i] = d[i - 1] + d[i - 2];coutn;for (int i = 1; i > a[i];sum += a[i];//这里有点疑问}memset(dp[0], -1, sizeof(dp[0]));// 初始化边际条件dp[0][0] = 0;int t = 1;for (int i = 1; i = 0)) // && 的短路操作dp[t][j] = max(dp[t][j], dp[t ^ 1][a[i] - j] + a[i] - j);if (j - a[i] >= 0 && dp[t ^ 1][j - a[i]] >= 0)dp[t][j] = max(dp[t][j], dp[t ^ 1][j - a[i]]);}t ^= 1; // 也可以将 所有的 t^1 换成: t = 1- t}cout = 0 && d[(i - 1) & 1][j - a[i]] >= 0)d[i & 1][j] = max(d[i & 1][j], d[(i - 1) & 1][j - a[i]]);}}printf("%d\n", d[n & 1][0] == 0 ? -1 : d[n & 1][0]);return 0;}

 

3.最长回文子序列(Palindromic sequence)

这里有几个概念最长公共子序列LCS,最长公共子串,最长回文子序列,最长回文子串,子序列通常要求元素之间不是连续,而子串要求元素之间必须是连续的。

LCS是最经典的动态规划例题,LPS最长回文子序列也是经常用得到,这里做一点探讨。(LCS 在之前一篇博文已经讲过了,这里只讲一下LPS)

求LPS有两种方法:

1)假设有一个序列S,其最长回文子序列为Sp,其逆序序列是ST,则 LPS(S)= Sp = LCS(S,ST),就是说最长回文子序列就是序列S与其逆序ST之间的最长公共子序列,这个很好理解,在求解时套用LCS的解法即可。这个思想已经可以很好的解决LPS的问题,只有一单缺点,就是逆序操作可能需要消耗一点时间和空间。

2)直接动态规划,列出状态转移方程。LPS(i,j)是 序列S(i,i+1,i+2,……j)的最长回文子序列

//动态规划求解最长回文子序列,时间复杂度为O(n^2)int lpsDp(char *str, int n){int dp[10][10], tmp;memset(dp, 0, sizeof(dp));for (int i = 0; i < n; ++i)dp[i][i] = 1;for (int i = 1; i < n; ++i){tmp = 0;//考虑所有连续的长度为i+1的子串,str[j....j+i]for (int j = 0; j + i < n; j++){if (str[j] == str[j + i])tmp = dp[j + 1][j + i - 1] + 2;else tmp = max(dp[j + 1][j + i], dp[j][j + i - 1]);dp[j][j + i] = tmp;}}return dp[0][n - 1]; //返回字符串str[0...n-1]的最长回文子序列长度}

例:poj1159 给你一个字符串,可在任意位置添加字符,最少再添加几个字符,可以使这个字符串成为回文字符串。(这一道用到了LPS和滚动数组。)

int FindLenLPS(int n){for (int i=0; i
免责声明:非本网注明原创的信息,皆为程序自动获取互联网,目的在于传递更多信息,并不代表本网赞同其观点和对其真实性负责;如此页面有侵犯到您的权益,请给站长发送邮件,并提供相关证明(版权证明、身份证正反面、侵权链接),站长将在收到邮件12小时内删除。

相关阅读

一周热门

查看更多