标签:mem for har 距离 否则 子序列 input 注意 需要
第1行:字符串A 第2行:字符串B (A,B的长度 <= 1000)
输出最长的子序列,如果有多个,随意输出1个。
abcicba abdkscab
abca
状态转移方程为dp[i][j] = a[i]==a[j]?dp[i-1][j-1]+1:max(dp[i-1][j],dp[i][j-1]),然后用dfs搜索回去
#include <iostream> #include <algorithm> #include <cmath> #include <vector> #include <string> #include <cstring> #pragma warning(disable:4996) using namespace std; char a[1005]; char b[1005]; int dp[1005][1005]; int pre[1005][1005]; void dfs(int m,int n) { if(m==0||n==0) return; if(pre[m][n]==1) { dfs(m-1,n-1); cout<<a[m]; } else if(pre[m][n]==2) { dfs(m-1,n); } else { dfs(m,n-1); } } int main() { int i,j,len1,len2; //memset(dp,0,sizeof(dp)); //memset(pre,0,sizeof(pre)); cin>>a+1>>b+1; len1=strlen(a+1); len2=strlen(b+1); for(i=1;i<=len1;i++) { for(j=1;j<=len2;j++) { if(a[i]==b[j]) { dp[i][j]=dp[i-1][j-1]+1; pre[i][j]=1; } else { if(dp[i-1][j]>dp[i][j-1]) { dp[i][j]=dp[i-1][j]; pre[i][j]=2; } else { dp[i][j]=dp[i][j-1]; pre[i][j]=3; } } } } dfs(len1,len2); cout<<endl; return 0; }
第1行:1个数N,N为序列的长度(2 <= N <= 50000) 第2 - N + 1行:每行1个数,对应序列的元素(-10^9 <= S[i] <= 10^9)
输出最长递增子序列的长度。
8 5 1 6 8 2 4 5 10
5
#include<stdio.h> #include<algorithm> #include<string.h> using namespace std; const int maxn = 1E4 * 5 + 10; int a[maxn],stk[maxn]; int main(){ int n; scanf("%d",&n); for(int i = 1 ; i <= n ; ++i){ scanf("%d",&a[i]); } int pcur = 0; for(int i = 1;i <= n;++i){ if(!pcur){ stk[pcur++] = a[i]; }else { if(a[i] > stk[pcur - 1]){ stk[pcur++] = a[i]; }else if(a[i] < stk[pcur - 1]){ int pos = lower_bound(stk,stk + pcur,a[i]) - stk; stk[pos] = a[i]; } } } printf("%d\n",pcur); return 0; }
第1行,2个整数,N和W中间用空格隔开。N为物品的数量,W为背包的容量。(1 <= N <= 100,1 <= W <= 10000) 第2 - N + 1行,每行2个整数,Wi和Pi,分别是物品的体积和物品的价值。(1 <= Wi, Pi <= 10000)
输出可以容纳的最大价值。
3 6 2 5 3 8 4 9
14
状态转移
dp[MAXN][10000] 表示前i个物品空间为v的价值
状态转移的方程有放和不放两种,可得:
dp[i][m] = max(dp[i-1][m]__不放,dp[i-1][m-w[i]]+v[i])
#include<iostream> #include<cstdio> #include<algorithm> using namespace std; const int MAXN =101; /* 状态转移 dp[MAXN][10000] 表示前i个物品空间为v的价值 状态转移的方程有放和不放两种,可得: dp[i][m] = max(dp[i-1][m]__不放,dp[i-1][m-w[i]]+v[i]) */ int dp[MAXN][10001]; int w[MAXN],v[MAXN]; int main() { int n,maxw,max_all=-1; scanf("%d%d",&n,&maxw); for(int i=0;i<n;i++) { scanf("%d%d",&w[i],&v[i]); if(i==0) { dp[0][w[i]] = v[i]; } else { for(int k=0;k<=maxw;k++) { if(k<w[i]) dp[i][k]=dp[i-1][k];//没有空间 else dp[i][k] = max(dp[i-1][k],dp[i-1][k-w[i]]+v[i]); max_all=max(max_all,dp[i][k]); } } } cout<<max_all<<endl; return 0;
第1行:字符串a(a的长度 <= 1000)。 第2行:字符串b(b的长度 <= 1000)。
输出a和b的编辑距离
kitten sitting
dp[i][j] = max(dp[i-1][j],dp[i][j-1])+1,
替换是,dp[i][j] = dp[i-1][j-1],当a[i]==b[j] 不必操作 dp[i][j]=dp[i-1][j-1]
可得
dp[i][j] = max(dp[i-1][j]+1,dp[i][j-1]+1,dp[i-1][j-1]+a[i]==b[j]?0:1)
标签:mem for har 距离 否则 子序列 input 注意 需要
原文地址:http://www.cnblogs.com/joeylee97/p/6144194.html