poj 1159 Palindrome lcs 滚动数组

来源:互联网 发布:网络统考成绩查询短信 编辑:程序博客网 时间:2024/06/04 17:55

题意:求长度为n的字符串最少需要添加几个字符可以使之成为回文串。
思路:求原串和反串的最长公共子序列。然后总长减去最大的lcs的值即可。
用int 内存占用约95M, 题目要求是64M显然超内存, 所以用short
int 。 还能用滚动数组。

#include<iostream>#include <cstdio>#include <cstring>#include<vector>using namespace std;const int MAXN=5005;char s1[MAXN], s2[MAXN];short int dp[MAXN][MAXN];short int Max(short int a, short int b){    if(a>b)    return a;    return b;}int main(){    int n;    while(~scanf("%d", &n))    {        scanf("%s", s1+1);        memset(dp, 0, sizeof(dp));        int len = strlen(s1+1);        for(int i=1;i<=len;++i)            s2[i]=s1[len-i+1];        s2[len+1]='\0';        for(int i=1;i<=len;i++)        {            for(int j=1;j<=len;++j)            {                if(s1[i]==s2[j])                    dp[i][j]=Max(dp[i-1][j-1]+1, dp[i][j]);                else                    dp[i][j]=Max(dp[i][j-1], dp[i-1][j]);            }        }        printf("%d\n", len-dp[len][len]);    }    return 0;}

滚动数组
每两行求一个lcs, 往下递推。

#include<iostream>#include <cstdio>#include <cstring>#include<vector>using namespace std;const int MAXN=5005;char s1[MAXN], s2[MAXN];short int dp[2][MAXN];short int Max(short int a, short int b){    if(a>b)        return a;    return b;}int main(){    int n;    while(~scanf("%d", &n))    {        scanf("%s", s1+1);        memset(dp, 0, sizeof(dp));        int len = strlen(s1+1);        for(int i=1;i<=len;++i)            s2[i]=s1[len-i+1];        unsigned short int MAX=0;        s2[len+1]='\0';        for(int i=1;i<=len;i++)        {            for(int j=1;j<=len;++j)            {                if(s1[i]==s2[j])                    dp[i%2][j]=Max(dp[(i-1)%2][(j-1)]+1, dp[i%2][j]);                else                    dp[i%2][j]=Max(dp[i%2][j-1], dp[(i-1)%2][j]);                //MAX=Max(dp[i%2][j],MAX);            }        }        printf("%d\n", len-dp[len%2][len]);    }    return 0;}