UVa1437&LA4394 StringPainter
来源:互联网 发布:mysql dmg for mac 编辑:程序博客网 时间:2024/06/01 21:46
错成狗,想漏好几处。
下面本体:
设原串为x,目标串为y
考虑y[i],易知有这么几种情况:
1.x[i]没被涂过色(必有x[i]==y[i])
2.x[i]被涂过色
这时又分为
a.x[i]是某次涂色的开始点
b.x[i]不是某次涂色的开始点(则要从前面某个y[k]==y[i]且被涂过色的k涂过来)
*1:注意“被涂过色”:如果没有这个限定,情况1会混进来,例子:
caa
ccc
1位置虽然颜色对了但是不是涂上的,不加限定答案就成0了
*2:并不一定是从y中i前面第一个满足y[i]==y[k]的地方涂过来,例子:
y=cabcbac 最优方案第3个c应该从第一个涂过来
下面考虑一串全部满足条件2的字符x[i]~x[j]
设f[i][j]表示这串字符涂成y[i]~y[j]的最少次数
考虑最后一个位置j,则j要么是a情况要么是b
若是a,则枚举k,此时就算k+1~j-1中间有y中和j同色的,因为没法涂到j,一定后来又被涂了其他颜色,不用考虑,所以答案为f[i][k]+f[k+1][i-1]
若是b,显然是f[i][j-1]+1
这样O(n^3)可求f[][]
接下来考虑没涂色的怎么办
可以这样:设g[i]表示把1~i涂对的最少次数
可以枚举最近一个没涂色的位置j
则j+1~i都被涂过色,符合f的条件。
g[i]=g[j-1]+f[j+1][i]
当然也有可能都被涂过色g[i]=f[1][i]
于是g[n]就是答案。
#include<stdio.h>#include<string.h>#define re(i,l,r) for(int i=l;i<=r;i++)#define NN 105#define MA 2000000000using namespace std;int f[NN][NN],g[NN],n;char x[NN],y[NN];int min(int x,int y){return x<y?x:y;}int workf(int l,int r){ if(l>r) return 0; if(f[l][r]<MA) return f[l][r]; int ret=MA; re(i,l,r-1) if(y[i]==y[r]) ret=min(ret,workf(l,i)+workf(i+1,r-1)); ret=min(ret,workf(l,r-1)+1); f[l][r]=ret; return ret;}int main(){ freopen("prac.in","r",stdin); //freopen("prac.out","w",stdout); while(scanf("%s%s",x+1,y+1)==2) { memset(f,0x7f,sizeof(f)); memset(g,0x7f,sizeof(g)); n=strlen(x+1); g[0]=0; re(i,1,n) { g[i]=workf(1,i); re(j,1,i) if(x[j]==y[j]) g[i]=min(g[i],g[j-1]+workf(j+1,i)); } printf("%d\n",g[n]); } return 0;}
0 0
- UVa1437&LA4394 StringPainter
- LA4394
- uva1437 String painter
- String Painter LA4394
- LA4394 区间dp
- LA4394 String painter 区间dp
- dp 专题系列(二):LA3983 Robotruck,LA4794 Sharing Chocolate,LA4394 String Painter,LA4327 Parade,Uva 10817
- 瀑布流分别用UIScrollView和UICollectionView的两种写法
- c语言while,switch语句常用代码
- js创建对象的几种常用方式小结(推荐)
- SQL学习笔记
- 自学MFC第一篇
- UVa1437&LA4394 StringPainter
- 八大排序算法-直接插入排序
- STM32采集频率-外部计数方式
- 多条件查询解决方案
- Javascript 面向对象编程(一):封装
- 杭电ACM HDU 2674 N!Again
- 如何区分汉字与英文
- 常用的HTTP方法
- *UVALive 6657 - GCD XOR(数学)