题目

以前做过的一道题, 今天又加了一种方法 整理了一下。。。。。

题意:给出一个字符串,问要将这个字符串变成回文串要添加最少几个字符。

方法一:

将该字符串与其反转求一次LCS,然后所求就是n减去 最长公共子串的长度。

额,,这个思路还是不是很好想。

LCS:

 #include<iostream>
#include<cstring>
#include<cstdio>
using namespace std;
const int maxn = +;
char s1[maxn], s2[maxn];
int d[][maxn], n;
int mmin(int a,int b)
{
return a>b?b:a;
}
int mmax(int a, int b)
{
return a<b?b:a;
}
void Lcs()
{
int i, j;
for(i = ; i <= n; i++)
for(j = ; j <= n; j++)
if(s1[i] == s2[j])
d[i%][j] = d[(i-)%][j-] + ;
else
d[i%][j] = mmax(d[(i-)%][j], d[(i%)][j-]);
}
int main()
{
int i;
while(cin>>n)
{
memset(d, , sizeof(d));
for(i=; i<=n; i++)
cin>>s1[i];
for(i = n; i >=; i--)
s2[i] = s1[n-i+];
Lcs();
cout<<n-d[n%][n]<<endl;
}
return ;
}

方法二:

这个是discuss里的方法。

设ch[1]..ch[n]表示字符串1至n位,i为左游标,j为右游标 ,则i从n递减,j从i开始递增。
min[i][j]表示i和j之间至少需要插入多少个字符才能对称,初始置全0 ,我们最终需要得到的值是min[1][n].

if(ch[i]==ch[j]) //如果两个游标所指字符相同,向中间缩小范围
min[i][j]=min[i+1][j-1];
else
min[i][j] = 1 + (min[i+1][j]和min[i][j-1]中的较小值); //如果不同,典型的状态转换方程

下面这个代码 是用的short int d[5000][5000]

在poj 可以水过,但是在hdu还超内存,,所有需要用滚动数组来 节省内存。

 #include<iostream>
#include<cstring>
#include<cstdio>
using namespace std; int mmin(int a,int b)
{
return a>b?b:a;
}
short int d[][];
int main()
{
int n,i,j;
char s[];
memset(d,,sizeof(d));
cin>>n;
for(i=; i<=n; i++)
cin>>s[i];
for(i=n; i>=; i--)
for(j=i+; j<=n; j++)
if(s[i]==s[j])
d[i][j]=d[i+][j-];
else
d[i][j]=mmin(d[i+][j],d[i][j-])+; cout<<d[][n]<<endl;
return ;
}

因为d[i][j] 算的时候只是与 d[i+1][j] 和 d[i][j+1]有关,所有可以开一个d[2][5000]的数组。

滚动数组节省内存:

 #include<iostream>
#include<cstring>
#include<cstdio>
using namespace std; int mmin(int a,int b)
{
return a>b?b:a;
}
int d[][];
int main()
{
int n,i,j;
char s[];
while(cin>>n)
{
memset(d, , sizeof(d));
for(i=; i<=n; i++)
cin>>s[i]; for(i=n; i>=; i--)
for(j=i+; j<=n; j++)
if(s[i]==s[j])
d[i%][j]=d[(i+)%][j-];
else
d[i%][j]=mmin(d[(i+)%][j],d[i%][j-])+; cout<<d[][n]<<endl;
}
return ;
}

贴一下别人博客里的滚动数组的介绍:

滚动数组 举个简单的例子:
int i,d[100];
d[0]=1;d[1]=1;
for(i=2;i<100;i++)
d[i]=d[i-1]+d[i-2];
printf("%d",d[99]);
上面这个循环d[i]只需要解集中的前2个解d[i-1]和d[i-2];
为了节约空间用滚动数组的方法

int d[3];
d[0]=1;d[1]=1;
for(i=2;i<100;i++)
d[i%3]=d[(i-1)%3]+d[(i-2)%3];
printf("%d",d[99%3]);

注意上面的运算,我们只留了最近的3个解,数组好象在“滚动?一样,所以叫滚动数组

对于二维数组也可以用这种方法 例如:
int i,j,d[100][100];
for(i=1;i<100;i++)
    for(j=0;j<100;j++)
        d[i][j]=d[i-1][j]+d[i][j-1];

上?的d[i][j]忪便赖于d[i-1][j],d[i][j-1];
迿用滚动数组
int i,,j,d[2][100];
for(i=1;i<100;i++)
    for(j=0;j<100;j++)
        d[i%2][j]=d[(i-1)%2][j]+d[i%2][j-1];

滚动数组实际是一种节约空间的办法,时间上没什么优势,多用于DP中,举个例子先: 
一个DP,平常如果需要1000×1000的空间,其实根据DP的特点,能以2×1000的空间解决问题,并且通过滚动,获得和1000×1000一样的效果。

hdu 1513 && 1159 poj Palindrome (dp, 滚动数组, LCS)的更多相关文章

  1. HDU 5617 Jam's maze dp+滚动数组

    题目链接: hdu: http://acm.hdu.edu.cn/showproblem.php?pid=5617 bc(中文):http://bestcoder.hdu.edu.cn/contest ...

  2. HDU - 4576 Robot(概率dp+滚动数组)

    题意:所有的格子围成一个圈,标号为1~n,若从格子1出发,每次指令告知行走的步数,但可能逆时针也可能顺时针走,概率都是1/2,那么问走了m次指令后位于格子l~r(1≤l≤r≤n)的概率. 分析: 1. ...

  3. hdu Max Sum Plus Plus(dp+滚动数组)

    原题链接:http://acm.hdu.edu.cn/showproblem.php?pid=1024 m为段,要深刻理解题意,并没有说是段与段要连接. 题解链接:http://blog.csdn.n ...

  4. HDU 1024 Max Sum Plus Plus --- dp+滚动数组

    HDU 1024 题目大意:给定m和n以及n个数,求n个数的m个连续子系列的最大值,要求子序列不想交. 解题思路:<1>动态规划,定义状态dp[i][j]表示序列前j个数的i段子序列的值, ...

  5. HDU 5119 Happy Matt Friends (背包DP + 滚动数组)

    题目链接:HDU 5119 Problem Description Matt has N friends. They are playing a game together. Each of Matt ...

  6. POJ 3666 Making the Grade (DP滚动数组)

    题意:农夫约翰想修一条尽量平缓的路,路的每一段海拔是A[i],修理后是B[i],花费|A[i] – B[i]|,求最小花费.(数据有问题,代码只是单调递增的情况) #include <stdio ...

  7. USACO 2009 Open Grazing2 /// DP+滚动数组oj26223

    题目大意: 输入n,s:n头牛 s个栅栏 输入n头牛的初始位置 改变他们的位置,满足 1.第一头与最后一头的距离尽量大 2.相邻两头牛之间的距离尽量满足 d=(s-1)/(n-1),偏差不超过1 3. ...

  8. poj - 1159 - Palindrome(滚动数组dp)

    题意:一个长为N的字符串( 3 <= N <= 5000).问最少插入多少个字符使其变成回文串. 题目链接:http://poj.org/problem?id=1159 -->> ...

  9. hdu 1513(dp+滚动数组)

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1513 思路:n这么大,可以采用滚动数组,然后就是求原串和反串的LCS了. #include<io ...

随机推荐

  1. Express/Koa/Hapi

    Express/Koa/Hapi 本文翻译自: https://www.airpair.com/node.js/posts/nodejs-framework-comparison-express-ko ...

  2. SQL SERVER时间函数

    本篇文章还是学习<程序员的SQL金典>内容的记录,此次将讲解的是SQL SERVER的时间函数. 本文只讲SQL SERVER支持的时间函数(其它数据库这里就不罗列了,想看更多的可以关注& ...

  3. 2013 Asia Hangzhou Regional Contest

    Lights Against Dudely http://acm.hdu.edu.cn/showproblem.php?pid=4770 15个位置,所以可以暴力枚举那些放,对于放的再暴力枚举哪个转, ...

  4. IIS7.5 自定义Html/shtml/htm...后缀映射

    以添加html后缀的文件的 映射为例: 1.打开iis管理器,点击 2.点击打开处理程序映射 3.添加托管处理程序映射 4.请求路径 *.html 类型: System.Web.UI.PageHand ...

  5. Linux下tcp协议socket的recv函数返回时机分析(粘包)

    http://www.vckbase.com/index.php/wv/10http://blog.csdn.net/zlzlei/article/details/7689409 文章一: 当前在网络 ...

  6. Apache Options Indexes FollowSymLinks之讲解

    禁止显示Apache目录列表-Indexes FollowSymLinks 如何修改目录的配置以禁止显示 Apache 目录列表. 缺省情况下如果你在浏览器输入地址: http://localhost ...

  7. Win 7怎样拒绝所有可移动存储设备的所有权限

    在Windows 7中,我们可拒绝对任何可移动存储类的权限.下面让我来教大家怎样在组策略中启用“所有可移动存储类:拒绝所有权限”策略,具体操作步骤如下所述: 步骤/方法 在开始搜索框中键入“gpedi ...

  8. POJ3250Bad Hair Day

    http://poj.org/problem?id=3250 题意 :  n个牛排成一列向右看,牛 i 能看到牛 j 的头顶,当且仅当牛 j 在牛 i 的右边并且牛 i 与牛 j 之间的所有牛均比牛 ...

  9. PHP-Phalcon框架中的数据库操作

    > 本文描述了PHP-Phalcon框架中数据库操作方法,主要讨论Phalcon框架的Model组件中的操作方法.更详细的Model介绍请参考:官方文档 1. 连接数据库 在Phalcon框架中 ...

  10. [Browsable(false)]

    1.c#方法上面的[Browsable(false)]是干吗用的? 答案:标明此对象不可被浏览,这样它就不会出现在设计器的属性窗口里了 看如下代码: /// <include file='Asp ...