51nod 1270 dp

http://www.51nod.com/onlineJudge/questionCode.html#!problemId=1270

简单的线性dp,最近狂刷水题真的是。。。药丸

差值最大得话要么是峰顶要么是最小的1,不可能处在中间状态,那样显然没有峰值的贡献大,想通这一点之后方程就好写了,

dp[i][0]表示第i个数取最小值的最大代价,dp[i][1]相反。

有 dp[i][0]=max(dp[i-1][0],dp[i-1][1]+a[i-1]-1);

dp[i][1]=max(dp[i-1][0]+a[i]-1,dp[i-1][1]+abs(a[i]-a[i-1]);

 1 #include<bits/stdc++.h>
 2 using namespace std;
 3 #define LL long long
 4 #define inf 0x3f3f3f3f
 5 LL mod=1e9+7;
 6 LL dp[50005][2];
 7 int a[50005];
 8 int main()
 9 {
10     int N,i,j;
11     cin>>N;
12     for(i=1;i<=N;++i) scanf("%d",a+i);
13     dp[2][0]=a[1]-1;
14     dp[2][1]=a[2]-1;
15     for(i=3;i<=N;++i)
16     {
17         dp[i][0]=max(dp[i-1][0],dp[i-1][1]+a[i-1]-1);
18         dp[i][1]=max(dp[i-1][0]+a[i]-1,dp[i-1][1]+abs(a[i]-a[i-1]));
19     }
20     cout<<max(dp[N][0],dp[N][1])<<endl;
21     return 0;
22 }
时间: 2024-08-03 03:43:15

51nod 1270 dp的相关文章

51nod 1154 dp

http://www.51nod.com/onlineJudge/questionCode.html#!problemId=1154 1154 回文串划分 基准时间限制:1 秒 空间限制:131072 KB 分值: 40 难度:4级算法题 收藏 关注 有一个字符串S,求S最少可以被划分为多少个回文串. 例如:abbaabaa,有多种划分方式. a|bb|aabaa - 3 个回文串 a|bb|a|aba|a - 5 个回文串 a|b|b|a|a|b|a|a - 8 个回文串 其中第1种划分方式的

51nod 1270 数组的最大代价 思路:简单动态规划

这题是看起来很复杂,但是换个思路就简单了的题目. 首先每个点要么取b[i],要么取1,因为取中间值毫无意义,不能增加最大代价S. 用一个二维数组做动态规划就很简单了. dp[i][0]表示第i个点取1时(第0-i个点)得到的最大代价之和. dp[i][1]表示第i个点取b[i]时(第0-i个点)得到的最大代价之和. 每一个都由前面两个推出. #include <bits\stdc++.h> using namespace std; int a[50005]; int dp[50005][2];

51nod 1270 数组的最大代价

感觉自己最近状态好差劲啊 做题都得提前看一下题解 不过这题也没那么难,可以大概知道的是  如果要满足代价最大,A[i]的值不是1就是B[i] #include<bits/stdc++.h> using namespace std; int s[50010],dp[50010][2]; int main () { int n; scanf("%d",&n); for(int i=1;i<=n;i++) scanf("%d",&s[i]

[51nod]A树的双直径

题目链接: 51nod 树形\(DP\)+换根\(DP\). 最直观的想法是枚举一条边断开,在两颗子树中求最大直径相乘然后取最大值. 不过这题可能出现负数,那么答案可能是正数\(\times\)正数或者负数\(\times\)负数. 其实只需要考虑正数的情况(负数把边全部取反即可) 那么设枚举边\((x,y)\),其中\(x\)为\(y\)的父亲 那么我们需要求出以\(y\)为根子树中的最长链和除去\(x\)子树外的最长链 对于\(y\)子树中的最长链\(InMax[y]\),我们可以先考虑求出

1270 数组的最大代价 dp

http://www.51nod.com/onlineJudge/questionCode.html#!problemId=1270&judgeId=194704 一开始贪心,以为就两种情况,大.小.大.小.....这样下去 小.大.小.大.....这样下去, 结果翻车.比如1.2.1.1.2.1这个样例 就不行了. 那么以dp[i][0]表示前i个数,第i个数选了小的数字,能产生的最大差值, dp[i][1]同理,转移的时候,上一唯也是两种情况,所以一共4中情况. #include <cs

51nod 1201 整数划分(dp)

题目链接:https://www.51nod.com/onlineJudge/questionCode.html#!problemId=1201 题解:显然是一道dp,不妨设dp[i][j]表示数字i分成j个一共有几种分法. 那么转移方程式为: dp[i][j] = dp[i - 1][j] + dp[i - 1][j - 1] 表示将i - 1划分为j个数,然后j个数都+1 还是不重复,将i - 1划分为j - 1个数,然后j - 1个数都+1,再加上1这个数. 然后就是j的范围要知道1+2+

51nod 1406 位运算/dp

http://www.51nod.com/onlineJudge/questionCode.html#!problemId=1406 1406 与查询 题目来源: CodeForces 基准时间限制:2 秒 空间限制:131072 KB 分值: 80 难度:5级算法题 收藏 关注 有n个整数.输出他之中和x相与之后结果为x的有多少个.x从0到1,000,000 Input 第一行输入一个整数n.(1<=n<=1,000,000). 第二行有n个整数a[0],a[1],a[2],...a[n-1

51nod 1412 AVL树的种类(经典dp)

http://www.51nod.com/onlineJudge/questionCode.html#!problemId=1412 题意: 思路: 经典dp!!!可惜我想不到!! $dp[i][k]$表示i个结点,最大深度为k的形态数. 它的转移方程就是: dp[i][k] += dp[i - 1 - j][k - 1] * dp[j][k - 1] dp[i][k] += 2 * dp[i - 1 - j][k - 2] * dp[j][k - 1] j是右子树结点个数,如果除去根结点,是不

51NOD 1202 子序列个数 DP

http://www.51nod.com/onlineJudge/questionCode.html#!problemId=1202&judgeId=225600 这题看起来挺复杂,但是真正的dp还是挺好理解的.唯独是想不到的,应该把样例模拟一遍. 比如1.2.4.2 考虑第一个,只有"1"这一个子序列 考虑前两个,有:"1", "12", "2" 前三个,有:"1", "12"