String painter
Time Limit: 5000/2000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others)
Total Submission(s): 1529 Accepted Submission(s): 680
Problem Description
There are two strings A and B with equal length. Both strings are made up of lower case letters. Now you have a powerful string painter. With the help of the painter, you can change a segment of characters of a string to any other
character you want. That is, after using the painter, the segment is made up of only one kind of character. Now your task is to change A to B using string painter. What’s the minimum number of operations?
Input
Input contains multiple cases. Each case consists of two lines:
The first line contains string A.
The second line contains string B.
The length of both strings will not be greater than 100.
The first line contains string A.
The second line contains string B.
The length of both strings will not be greater than 100.
Output
A single line contains one integer representing the answer.
Sample Input
zzzzzfzzzzz abcdefedcba abababababab cdcdcdcdcdcd
Sample Output
6 7
Source
题意:
有两个字符串长度同样,如今有一个painter,一次能够把第一个字符串中的一段区间内的全部字母都换成同一个字母(这个字母能够是随意一个),问最少运行多少次操作,才干将第一个字符串s1转换成第二个字符串s2.
思路:
先将空白串变为s2,dp[i][j]-将i~j刷为目标串所须要的步数。
dp[i][j]=dp[i][j-1]+1; j单独刷
当s[j]==s[k]时,j能够借助刷k的时候一起刷,dp[i][j]=min(dp[i][j],dp[i][k]+dp[k+1][j-1]);
处理完后,我们就要看s1须要喷刷多少次到s2了,s1比空白串的长处在哪里呢?在于s1有与s2同样的字符,这些字符能够不用个刷本身就与s2同样,用res[i]记录1~i区间第二个字符串得出的喷刷次数,假设第一个字符串的i位置与第二个字符串的i位置同样,那么这个位置就不用喷刷了,res[i]=res[i-1],假设不同样,就要就要借助一个位于1~(i-1)区间内的变量来切割开,res[i]=min(res[i],res[j]+dp[j+1][i])。
代码:
#include <iostream> #include <cstdio> #include <cstring> #include <algorithm> #include <cmath> #include <string> #include <map> #include <stack> #include <vector> #include <set> #include <queue> #define maxn 105 #define MAXN 100005 #define mod 100000000 #define INF 0x3f3f3f3f #define pi acos(-1.0) #define eps 1e-6 typedef long long ll; using namespace std; int n,m,ans,cnt,tot; char s1[maxn],s2[maxn]; int dp[maxn][maxn],res[maxn]; int main() { int i,j,t,k,len; while(~scanf("%s%s",s1+1,s2+1)) { memset(dp,0,sizeof(dp)); n=strlen(s1+1); for(i=1;i<=n;i++) { dp[i][i]=1; } for(len=2;len<=n;len++) { for(i=1;i<=n;i++) { j=i+len-1; if(j>n) break ; dp[i][j]=dp[i][j-1]+1; for(k=i;k<j;k++) { if(s2[k]==s2[j]) dp[i][j]=min(dp[i][j],dp[i][k]+dp[k+1][j-1]); } } } for(i=1;i<=n;i++) { res[i]=dp[1][i]; } for(i=1;i<=n;i++) { if(s1[i]==s2[i]) res[i]=res[i-1]; else { for(j=1;j<i;j++) { res[i]=min(res[i],res[j]+dp[j+1][i]); } } } printf("%d ",res[n]); } return 0; }