CodeForces 484D Kindergarten
题目描述:
输入一个 N 个数的序列,将其划分成若干段,每段的权值等于其最大值减去最小值,求最大的权值和。
题解:
显然划分出来的每一段都应当是单调的,唯一的问题就是局部极值点划分到左边还是右边,于是直接 O(N) DP 即可。
代码:
#include <cstdio>
#include <cstdlib>
#include <algorithm>
using namespace std;
#define MAXN 1000007
static int N;
static long long val[MAXN], dp[MAXN];
int main()
{
scanf("%d", &N);
for (int i = 0; i < N; i++) scanf("%lld", &val[i]);
dp[1] = abs(val[1] - val[0]);
for (int i = 2; i < N; i++)
if ((val[i-2] <= val[i-1] && val[i-1] >= val[i]) || (val[i-2] >= val[i-1] && val[i-1] <= val[i]))
dp[i] = max(dp[i-1], dp[i-2] + abs(val[i] - val[i-1]));
else
dp[i] = dp[i-1] + abs(val[i] - val[i-1]);
printf("%lld\n", dp[N-1]);
return 0;
}
提交记录(AC / Total = 1 / 2):
Run ID | Remote Run ID | Time(ms) | Memory(kb) | Result | Submit Time |
---|---|---|---|---|---|
8771973 | 26348393 | 30 | 3420 | WA | 2017-04-14 07:22:22 |
8771974 | 26348412 | 280 | 17512 | AC | 2017-04-14 07:25:25 |