题目
题解
首先我们需要知道,如果前一份订单都不满足,那么之后的所有订单都不用继续考虑;而如果后一份订单都满足,那么之前的所有订单一定都可以满足, 所以就很显然了。
差分 + 二分
code
#include <algorithm>
#include <cctype>
#include <cmath>
#include <complex>
#include <cstdio>
#include <cstring>
#include <deque>
#include <functional>
#include <list>
#include <map>
#include <iomanip>
#include <iostream>
#include <set>
#include <queue>
#include <stack>
#include <string>
#include <vector>
#define sys system("PAUSE")
using namespace std;
const int maxn = 1e6 + 1000;
typedef long long ull;
inline int read() {
int s = 0, w = 1;
char ch = getchar();
while (!isdigit(ch)) { if (ch == '-') w = -1; ch = getchar(); }
while (isdigit(ch)) { s = (s << 1) + (s << 3) + (ch ^ 48); ch = getchar(); }
return s * w;
}
int n, m;
int rt[maxn], d[maxn], r[maxn], l[maxn], c[maxn], sum[maxn];
int begin, end;
inline bool check(int k) {
memset(c, 0, sizeof(c));
for (int i = 1; i <= k; ++i) {
c[l[i]] += d[i];
c[r[i] + 1] -= d[i];
}
for (int i = 1; i <= n; ++i) {
sum[i] = sum[i - 1] + c[i];
if (sum[i] > rt[i]) return false;
}
return true;
}
int main() {
n = read(), m = read();
for (int i = 1; i <= n; ++i) rt[i] = read();
for (int i = 1; i <= m; ++i) {
d[i] = read(), l[i] = read(), r[i] = read();
}
begin = 1, end = m;
if (check(m)) {
printf("0\n");
// sys;
exit(0);
}
while (begin < end) {
int mid = (begin + end) >> 1;
if (check(mid)) begin = mid + 1;
else end = mid;
}
printf("%d\n%d\n", -1, begin);
// sys;
return 0;
}