The LCS problem, also known as the longest common subsequence problem, is a simpler one in DP, so let's take a brief look at it today.
Set S1:aeglegllelgel
Set S2:lregelgegleg
To find the maximum common subsequence length of a two string
Output: 8
DP[I][J] represents the maximum common subsequence length that is obtained from the first J of the S1 and S2.
Transfer equation:
Dp[i][j]=0 (i==0| | j==0)
Dp[i][j]=max (Dp[i-1][j-1]+same (i,j), Max (dp[i-1][j],dp[i][j-1]));
Same (I,J) = (s1[i]==s2[j]?1:0)
Look at a topic (HDU1243)
Test instructions: The length of the maximum common sub-sequence of two strings
Analysis: DP, matched to the same weight as the letter
//Common sub-sequence problems//Dp[i][j] Represents the largest common sub-sequence obtained by the first I of the former S1 and the first J of S#include <cstdio>#include<cstring>#include<algorithm>using namespacestd;intn,value[ $],dp[2005][2005];Chars1[2005],s2[2005];intMain () { while(SCANF ("%d", &n)!=-1) {scanf ("%s", s1+1); for(intI=1; i<=n;++i) scanf ("%d",&Value[s1[i]]); scanf ("%s", S1); GetChar (); scanf ("%s", S2); //memset (Dp,0,sizeof (DP)); intLen1=strlen (S1), len2=strlen (S2); for(intI=0; i<=len1;++i) dp[i][0]=0; for(intI=0; i<=len2;++i) dp[0][i]=0; for(intI=0; i<len1;++i) for(intj=0; j<len2;++j) {Dp[i+1][j+1]=max (dp[i][j]+ (S1[i]==s2[j]) Value[s1[i]:0), Max (dp[i][j+1],dp[i+1][j])); } printf ("%d\n", Dp[len1][len2]); }}
View Code
What if the maximum common subsequence is output?
Simply add an array of f[i][j] to record the matching situation
F[i][j]=0 (S1[i]==s2[j])
F[i][j]=1 (Dp[i][j+1]>dp[i+1][j])
f[i][j]=2 (Dp[i][j+1]<=dp[i+1][j])
or HDU1243?
Input
4
Abcd
1 1 1 1
Abcabcabc
Dacdbdb
Output
Acbb
4
//Common sub-sequence problems//Dp[i][j] Represents the largest common sub-sequence obtained by the first I of the former S1 and the first J of S#include <cstdio>#include<cstring>#include<algorithm>using namespacestd;intn,value[ $],dp[2005][2005],f[2005][2005] ;Chars1[2005],s2[2005];void out(intXinty) { if(x==0|| y==0)return ; if(f[x][y]==0) { out(X-1, Y1); printf ("%c", s1[x-1]); } Else if(f[x][y]==1) out(X-1, y); Else out(x,y-1);}intMain () { while(SCANF ("%d", &n)!=-1) {scanf ("%s", s1+1); for(intI=1; i<=n;++i) scanf ("%d",&Value[s1[i]]); scanf ("%s", S1); GetChar (); scanf ("%s", S2); //memset (Dp,0,sizeof (DP)); intLen1=strlen (S1), len2=strlen (S2); for(intI=0; i<=len1;++i) dp[i][0]=0; for(intI=0; i<=len2;++i) dp[0][i]=0; for(intI=0; i<len1;++i) for(intj=0; j<len2;++j) {if(S1[i]==s2[j]) {dp[i+1][j+1]=dp[i][j]+value[s1[i]];f[i+1][j+1]=0;} Else{f[i+1][j+1]= ((dp[i][j+1]>dp[i+1][J])?1:2); Dp[i+1][j+1]=max (dp[i][j+1],dp[i+1][j]); } } out(LEN1,LEN2); Puts (""); printf ("%d\n", Dp[len1][len2]); }}
View Code
Maximum Common substring problem
This problem is the distortion of the LCS, more simple
DP[I][J] represents the maximum common substring length that is obtained from the first J of the S1 and S2.
Dp[i][j]=dp[i-1][j-1]+1 (S1[i]==s2[j])
Dp[i][j]=0 (S1[i]!=s2[j])
If you want to lose a substring, record the maximum length and then output it back
#include <cstdio>#include<cstring>#include<algorithm>using namespacestd;intmax_len,dp[1010][1010],t,len1,len2;Chars1[1010],s2[1010];intMain () { for(SCANF ("%d", &t); t--;) {scanf ("%s%s", S1,S2); Len1=strlen (S1), len2=strlen (S2); Max_len=0; for(intI=1; i<=len1;++i) dp[i][0]=0; for(intI=1; i<=len2;++i) dp[0][i]=0; for(intI=1; i<=len1;++i) for(intj=1; j<=len2;++j) {if(s1[i-1]==s2[j-1]) dp[i][j]=dp[i-1][j-1]+1; Elsedp[i][j]=0; Max_len=Max (max_len,dp[i][j]); } printf ("%d\n", Max_len); }}
View Code
"Algorithm Small summary" LCS problem &&hdu1243