洛谷P4552 [Poetize6] IncDec Sequence 题解 差分数组
题目链接:https://www.luogu.com.cn/problem/P4552
解题思路:设差分数组 \(d[i] = a[i] - a[i-1]\),用 \(sump\) 表示所有 \(\gt 0\) 的 \(d[i]\) 之和;用 \(sumn\) 表示所有 \(\lt 0\) 的 \(d[i]\) 的绝对值之和。
则因为一开始需要操作的是尽可能地消掉一个差分数组中的 \(+1\) 和 \(-1\)。后期只需要消掉一个 \(+1\) 或 \(-1\) 即可。所以:
- 最少操作次数为 \(\max \{ sump, sumn \}\)
- 结果数为 \(|sump - sumn| + 1\)
示例代码:
#include <bits/stdc++.h>
using namespace std;
const int maxn = 100010;
long long n, a[maxn], d[maxn], sump, sumn;
int main() {
cin >> n;
for (int i = 1; i <= n; i ++) cin >> a[i];
for (int i = 2; i <= n; i ++) {
d[i] = a[i] - a[i-1];
if (d[i] > 0) sump += d[i];
else sumn += abs(d[i]);
}
cout << max(sump, sumn) << endl << abs(sump - sumn) + 1 << endl;
return 0;
}
再简化一些的代码:
#include <bits/stdc++.h>
using namespace std;
const int maxn = 100010;
long long n, a[maxn], d, sump, sumn;
int main() {
cin >> n;
for (int i = 1; i <= n; i ++) cin >> a[i];
for (int i = 2; i <= n; i ++) {
d = a[i] - a[i-1];
if (d > 0) sump += d;
else sumn += abs(d);
}
cout << max(sump, sumn) << endl << abs(sump - sumn) + 1 << endl;
return 0;
}