动态规划题目小结
2013-05-14 20:25
405 查看
前两天省赛结束了,为了它我们集训了两个月,从早到晚,但是结果却不是我们想要的结果,与金奖失之交臂了........
经过这次比赛,我们发现我们队的dp简直弱爆了,因此我决定来好好的学学动态规划这个非常奇妙的东西,写篇博客记录下
NYOJ 708 ones
n给一个整数n,要你找一个值为n的表达式,这个表达式只有1 + * ( )够成。并且1不能连续,比如11+1就不合法。
n输入n,(1<=n<=10000)
n输出最少需要多少个1才能构成表达式。
n样例:n=2=1+1 ans=2
n=10=(1+1)*(1+1+1+1+1) ans=7
dp[i]表示最少数量的1能够表示i,分为两种情况,加法和乘法,状态转移方程式为
add: dp[ i ] = dp[ j ] + dp[ i - j ] 0<j<i
multiply: dp[ i ] = dp[ j ] + dp[ i / j ] 0<j<i, i%j=0
NYOJ 716 River Crossing
省赛的题目,就是因为这道题与金奖擦肩而过,遗憾呀! 当时没想到用动态规划,以为是贪心来做的,结果一直到最后都没做出来。
一个完全背包的变形题,背包的体积为羊的总个数,物品的价值为花费的时间,怎样花费最少的时间将羊运过河
状态转移方程为:dp[j]=dp[j-i]+a[i]+2*m; m为船走一趟花费的时间
刘汝佳《算法竞赛入门经典-训练指南》的动态规划部分的习题 打开
Problem one
11584 - Partitioning
by Palindromes 简单线性dp
dp[ i ] 表示以 i 结尾的最小回文区间数
dp[ i ] = min(dp[ i ] , dp[ j ] + 1)(区间( j , i )是一个回文区间)
未完待续。。。。。
经过这次比赛,我们发现我们队的dp简直弱爆了,因此我决定来好好的学学动态规划这个非常奇妙的东西,写篇博客记录下
NYOJ 708 ones
n给一个整数n,要你找一个值为n的表达式,这个表达式只有1 + * ( )够成。并且1不能连续,比如11+1就不合法。
n输入n,(1<=n<=10000)
n输出最少需要多少个1才能构成表达式。
n样例:n=2=1+1 ans=2
n=10=(1+1)*(1+1+1+1+1) ans=7
dp[i]表示最少数量的1能够表示i,分为两种情况,加法和乘法,状态转移方程式为
add: dp[ i ] = dp[ j ] + dp[ i - j ] 0<j<i
multiply: dp[ i ] = dp[ j ] + dp[ i / j ] 0<j<i, i%j=0
#include<cstdio> #include<iostream> using namespace std; const int N = 10005; int dp ; void fun() { int i,j; dp[0] = 0; dp[1] = 1; for(i =2; i <= 10000; i++) { dp[i] = i; for(j = 1; j < i; j++) { dp[i] = min(dp[i],(dp[i - j] + dp[j])); if(i % j == 0) dp[i] = min(dp[i],dp[j] + dp[i / j]); } } } int main() { int n; fun(); while(~scanf("%d",&n)) { printf("%d\n",dp ); } return 0; }
NYOJ 716 River Crossing
省赛的题目,就是因为这道题与金奖擦肩而过,遗憾呀! 当时没想到用动态规划,以为是贪心来做的,结果一直到最后都没做出来。
一个完全背包的变形题,背包的体积为羊的总个数,物品的价值为花费的时间,怎样花费最少的时间将羊运过河
状态转移方程为:dp[j]=dp[j-i]+a[i]+2*m; m为船走一趟花费的时间
#include<cstdio> #include<cstring> #include<iostream> using namespace std; const int Max=0x7fffffff; int a[1005]; int dp[1005]; int main() { int n,m,i,j,t,k; scanf("%d",&t); while(t--) { scanf("%d%d",&n,&m); a[0]=0; dp[0]=0; for(i = 1; i <= n; i++) { scanf("%d",&k); a[i] = a[i-1] + k; dp[i]=Max; //初始化为极大值 } for(i = 1; i <= n; i++) for(j = 1; j <= n; j++) { if(dp[j]>dp[j-i]+a[i]+2*m) dp[j]=dp[j-i]+a[i]+2*m; } printf("%d\n",dp -m); } return 0; }
刘汝佳《算法竞赛入门经典-训练指南》的动态规划部分的习题 打开
Problem one
11584 - Partitioning
by Palindromes 简单线性dp
dp[ i ] 表示以 i 结尾的最小回文区间数
dp[ i ] = min(dp[ i ] , dp[ j ] + 1)(区间( j , i )是一个回文区间)
#include<iostream> #include<cstdio> #include<cstring> using namespace std; char ch[5005]; int dp[5005]; bool check(int x,int y) { while(x <= y) { if(ch[x] != ch[y]) return false; x++; y--; } return true; } int main() { //freopen("Input.txt","r",stdin); int t,i,j; scanf("%d",&t); while(t--) { scanf("%s",ch+1); int len = strlen(ch+1); //memset(dp,0,sizeof(dp)); for(i = 1; i <= len; i++) { dp[i] = i; for(j = 1; j <= i; j++) { if(ch[j] == ch[i] && check(j,i)) { dp[i] = min(dp[i],dp[j-1]+1); } } } printf("%d\n",dp[len]); } return 0; }
未完待续。。。。。
相关文章推荐
- 动态规划部分题目小结
- 动态规划经典题目:最大连续子序列和
- 算法刷题:LeetCode中常见的动态规划题目
- Problem A: 动态规划基础题目之数字三角形
- NYOJ 题目79 拦截导弹(动态规划,最长递增子序列)
- POJ动态规划题目列表
- HDOJ 题目1284钱币兑换问题(动态规划,完全背包)
- 动态规划经典题目:最大连续子序列和
- poj 未解动态规划题目
- 动态规划题目
- Poj动态规划题目列表
- POJ动态规划题目列表
- POJ动态规划题目列表
- YTU OJ 3136: 动态规划基础题目之最长公共子序列
- 动态规划题目集锦
- 剑指offer 07-10 斐波那契数列类型题目的动态规划解题方法(递归方法)
- acm之动态规划题目1
- 自己的动态规划题目(持续更新)
- LeetCode中的两道动态规划题目
- 动态规划题目