QOJ.ac
QOJ
ID | Problem | Submitter | Result | Time | Memory | Language | File size | Submit time | Judge time |
---|---|---|---|---|---|---|---|---|---|
#311816 | #4780. 完美的队列 | hos_lyric | 0 | 661ms | 47056kb | C++14 | 13.9kb | 2024-01-22 20:29:41 | 2024-01-22 20:29:41 |
Judging History
answer
#include <cassert>
#include <cmath>
#include <cstdint>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <algorithm>
#include <bitset>
#include <complex>
#include <deque>
#include <functional>
#include <iostream>
#include <limits>
#include <map>
#include <numeric>
#include <queue>
#include <random>
#include <set>
#include <sstream>
#include <string>
#include <unordered_map>
#include <unordered_set>
#include <utility>
#include <vector>
using namespace std;
using Int = long long;
template <class T1, class T2> ostream &operator<<(ostream &os, const pair<T1, T2> &a) { return os << "(" << a.first << ", " << a.second << ")"; };
template <class T> ostream &operator<<(ostream &os, const vector<T> &as) { const int sz = as.size(); os << "["; for (int i = 0; i < sz; ++i) { if (i >= 256) { os << ", ..."; break; } if (i > 0) { os << ", "; } os << as[i]; } return os << "]"; }
template <class T> void pv(T a, T b) { for (T i = a; i != b; ++i) cerr << *i << " "; cerr << endl; }
template <class T> bool chmin(T &t, const T &f) { if (t > f) { t = f; return true; } return false; }
template <class T> bool chmax(T &t, const T &f) { if (t < f) { t = f; return true; } return false; }
#define COLOR(s) ("\x1b[" s "m")
// T: monoid representing information of an interval.
// T() should return the identity.
// T(S s) should represent a single element of the array.
// T::pull(const T &l, const T &r) should pull two intervals.
template <class T> struct SegmentTreePoint {
int logN, n;
vector<T> ts;
SegmentTreePoint() : logN(0), n(0) {}
explicit SegmentTreePoint(int n_) {
for (logN = 0, n = 1; n < n_; ++logN, n <<= 1) {}
ts.resize(n << 1);
}
template <class S> explicit SegmentTreePoint(const vector<S> &ss) {
const int n_ = ss.size();
for (logN = 0, n = 1; n < n_; ++logN, n <<= 1) {}
ts.resize(n << 1);
for (int i = 0; i < n_; ++i) at(i) = T(ss[i]);
build();
}
T &at(int i) {
return ts[n + i];
}
void build() {
for (int u = n; --u; ) pull(u);
}
inline void pull(int u) {
ts[u].pull(ts[u << 1], ts[u << 1 | 1]);
}
// Changes the value of point a to s.
template <class S> void change(int a, const S &s) {
assert(0 <= a); assert(a < n);
ts[a += n] = T(s);
for (; a >>= 1; ) pull(a);
}
// Applies T::f(args...) to point a.
template <class F, class... Args>
void ch(int a, F f, Args &&... args) {
assert(0 <= a); assert(a < n);
(ts[a += n].*f)(args...);
for (; a >>= 1; ) pull(a);
}
// Calculates the product for [a, b).
T get(int a, int b) {
assert(0 <= a); assert(a <= b); assert(b <= n);
if (a == b) return T();
a += n; b += n;
T prodL, prodR, t;
for (int aa = a, bb = b; aa < bb; aa >>= 1, bb >>= 1) {
if (aa & 1) { t.pull(prodL, ts[aa++]); prodL = t; }
if (bb & 1) { t.pull(ts[--bb], prodR); prodR = t; }
}
t.pull(prodL, prodR);
return t;
}
// Calculates T::f(args...) of a monoid type for [a, b).
// op(-, -) should calculate the product.
// e() should return the identity.
template <class Op, class E, class F, class... Args>
#if __cplusplus >= 201402L
auto
#else
decltype((std::declval<T>().*F())())
#endif
get(int a, int b, Op op, E e, F f, Args &&... args) {
assert(0 <= a); assert(a <= b); assert(b <= n);
if (a == b) return e();
a += n; b += n;
auto prodL = e(), prodR = e();
for (int aa = a, bb = b; aa < bb; aa >>= 1, bb >>= 1) {
if (aa & 1) prodL = op(prodL, (ts[aa++].*f)(args...));
if (bb & 1) prodR = op((ts[--bb].*f)(args...), prodR);
}
return op(prodL, prodR);
}
// Find min b s.t. T::f(args...) returns true,
// when called for the partition of [a, b) from left to right.
// Returns n + 1 if there is no such b.
template <class F, class... Args>
int findRight(int a, F f, Args &&... args) {
assert(0 <= a); assert(a <= n);
if ((T().*f)(args...)) return a;
if (a == n) return n + 1;
a += n;
for (; ; a >>= 1) if (a & 1) {
if ((ts[a].*f)(args...)) {
for (; a < n; ) {
if (!(ts[a <<= 1].*f)(args...)) ++a;
}
return a - n + 1;
}
++a;
if (!(a & (a - 1))) return n + 1;
}
}
// Find max a s.t. T::f(args...) returns true,
// when called for the partition of [a, b) from right to left.
// Returns -1 if there is no such a.
template <class F, class... Args>
int findLeft(int b, F f, Args &&... args) {
assert(0 <= b); assert(b <= n);
if ((T().*f)(args...)) return b;
if (b == 0) return -1;
b += n;
for (; ; b >>= 1) if ((b & 1) || b == 2) {
if ((ts[b - 1].*f)(args...)) {
for (; b <= n; ) {
if (!(ts[(b <<= 1) - 1].*f)(args...)) --b;
}
return b - n - 1;
}
--b;
if (!(b & (b - 1))) return -1;
}
}
};
////////////////////////////////////////////////////////////////////////////////
// T: monoid representing information of an interval.
// T() should return the identity.
// T(S s) should represent a single element of the array.
// T::push(T &l, T &r) should push the lazy update.
// T::pull(const T &l, const T &r) should pull two intervals.
template <class T> struct SegmentTreeRange {
int logN, n;
vector<T> ts;
SegmentTreeRange() : logN(0), n(0) {}
explicit SegmentTreeRange(int n_) {
for (logN = 0, n = 1; n < n_; ++logN, n <<= 1) {}
ts.resize(n << 1);
}
template <class S> explicit SegmentTreeRange(const vector<S> &ss) {
const int n_ = ss.size();
for (logN = 0, n = 1; n < n_; ++logN, n <<= 1) {}
ts.resize(n << 1);
for (int i = 0; i < n_; ++i) at(i) = T(ss[i]);
build();
}
T &at(int i) {
return ts[n + i];
}
void build() {
for (int u = n; --u; ) pull(u);
}
inline void push(int u) {
ts[u].push(ts[u << 1], ts[u << 1 | 1]);
}
inline void pull(int u) {
ts[u].pull(ts[u << 1], ts[u << 1 | 1]);
}
// Applies T::f(args...) to [a, b).
template <class F, class... Args>
void ch(int a, int b, F f, Args &&... args) {
assert(0 <= a); assert(a <= b); assert(b <= n);
if (a == b) return;
a += n; b += n;
for (int h = logN; h; --h) {
const int aa = a >> h, bb = b >> h;
if (aa == bb) {
if ((aa << h) != a || (bb << h) != b) push(aa);
} else {
if ((aa << h) != a) push(aa);
if ((bb << h) != b) push(bb);
}
}
for (int aa = a, bb = b; aa < bb; aa >>= 1, bb >>= 1) {
if (aa & 1) (ts[aa++].*f)(args...);
if (bb & 1) (ts[--bb].*f)(args...);
}
for (int h = 1; h <= logN; ++h) {
const int aa = a >> h, bb = b >> h;
if (aa == bb) {
if ((aa << h) != a || (bb << h) != b) pull(aa);
} else {
if ((aa << h) != a) pull(aa);
if ((bb << h) != b) pull(bb);
}
}
}
// Calculates the product for [a, b).
T get(int a, int b) {
assert(0 <= a); assert(a <= b); assert(b <= n);
if (a == b) return T();
a += n; b += n;
for (int h = logN; h; --h) {
const int aa = a >> h, bb = b >> h;
if (aa == bb) {
if ((aa << h) != a || (bb << h) != b) push(aa);
} else {
if ((aa << h) != a) push(aa);
if ((bb << h) != b) push(bb);
}
}
T prodL, prodR, t;
for (int aa = a, bb = b; aa < bb; aa >>= 1, bb >>= 1) {
if (aa & 1) { t.pull(prodL, ts[aa++]); prodL = t; }
if (bb & 1) { t.pull(ts[--bb], prodR); prodR = t; }
}
t.pull(prodL, prodR);
return t;
}
// Calculates T::f(args...) of a monoid type for [a, b).
// op(-, -) should calculate the product.
// e() should return the identity.
template <class Op, class E, class F, class... Args>
#if __cplusplus >= 201402L
auto
#else
decltype((std::declval<T>().*F())())
#endif
get(int a, int b, Op op, E e, F f, Args &&... args) {
assert(0 <= a); assert(a <= b); assert(b <= n);
if (a == b) return e();
a += n; b += n;
for (int h = logN; h; --h) {
const int aa = a >> h, bb = b >> h;
if (aa == bb) {
if ((aa << h) != a || (bb << h) != b) push(aa);
} else {
if ((aa << h) != a) push(aa);
if ((bb << h) != b) push(bb);
}
}
auto prodL = e(), prodR = e();
for (int aa = a, bb = b; aa < bb; aa >>= 1, bb >>= 1) {
if (aa & 1) prodL = op(prodL, (ts[aa++].*f)(args...));
if (bb & 1) prodR = op((ts[--bb].*f)(args...), prodR);
}
return op(prodL, prodR);
}
// Find min b s.t. T::f(args...) returns true,
// when called for the partition of [a, b) from left to right.
// Returns n + 1 if there is no such b.
template <class F, class... Args>
int findRight(int a, F f, Args &&... args) {
assert(0 <= a); assert(a <= n);
if ((T().*f)(args...)) return a;
if (a == n) return n + 1;
a += n;
for (int h = logN; h; --h) push(a >> h);
for (; ; a >>= 1) if (a & 1) {
if ((ts[a].*f)(args...)) {
for (; a < n; ) {
push(a);
if (!(ts[a <<= 1].*f)(args...)) ++a;
}
return a - n + 1;
}
++a;
if (!(a & (a - 1))) return n + 1;
}
}
// Find max a s.t. T::f(args...) returns true,
// when called for the partition of [a, b) from right to left.
// Returns -1 if there is no such a.
template <class F, class... Args>
int findLeft(int b, F f, Args &&... args) {
assert(0 <= b); assert(b <= n);
if ((T().*f)(args...)) return b;
if (b == 0) return -1;
b += n;
for (int h = logN; h; --h) push((b - 1) >> h);
for (; ; b >>= 1) if ((b & 1) || b == 2) {
if ((ts[b - 1].*f)(args...)) {
for (; b <= n; ) {
push(b - 1);
if (!(ts[(b <<= 1) - 1].*f)(args...)) --b;
}
return b - n - 1;
}
--b;
if (!(b & (b - 1))) return -1;
}
}
};
////////////////////////////////////////////////////////////////////////////////
struct NodeSum {
int sum;
NodeSum(int sum_ = 0) : sum(sum_) {}
void pull(const NodeSum &l, const NodeSum &r) {
sum = l.sum + r.sum;
}
bool test(int &tar) {
if (tar <= sum) return true;
tar -= sum;
return false;
}
};
constexpr int INF = 1001001001;
struct NodeMax {
int mx;
int lz;
NodeMax() : mx(-INF), lz(0) {}
NodeMax(int val) : mx(val), lz(0) {}
void push(NodeMax &l, NodeMax &r) {
if (lz) {
l.add(lz);
r.add(lz);
lz = 0;
}
}
void pull(const NodeMax &l, const NodeMax &r) {
mx = max(l.mx, r.mx);
}
void add(int val) {
mx += val;
lz += val;
}
// leaf
void change(int val) {
mx = val;
}
};
////////////////////////////////////////////////////////////////////////////////
int N, Q;
vector<int> A;
vector<int> L, R, X;
int segN;
vector<vector<int>> qss, rss;
SegmentTreePoint<NodeSum> above;
vector<vector<int>> addss, remss;
void exists(int q, int r) {
// cerr<<"exists "<<q<<" "<<r<<endl;
addss[q].emplace_back(X[q]);
remss[r].emplace_back(X[q]);
}
void dfs(int u, int L0, int R0) {
/*
above: cover above
qss[u]: cover exactly
qqss[u]: cover partially below
*/
const auto &qs = qss[u];
auto &rs = rss[u];
// if(qs.size()){cerr<<COLOR("33")<<u<<" "<<L0<<" "<<R0<<": "<<qs<<" "<<rs<<"; ";for(int q=0;q<Q;++q)cerr<<above.get(q,q+1).sum<<" ";cerr<<COLOR()<<endl;}
rs.push_back(Q);
for (const int q : qs) above.change(q, 1);
// start with HP of A[i]
SegmentTreeRange<NodeMax> seg(R0 - L0);
for (int i = L0; i < R0; ++i) if (i < N) {
seg.at(i - L0) = A[i];
}
seg.build();
auto below = [&](int j, int val) -> void {
int l = L[rs[j]] - L0;
int r = R[rs[j]] - L0;
chmax(l, 0);
chmin(r, R0 - L0);
seg.ch(l, r, &NodeMax::add, val);
};
int j0 = 0, j1 = 0;
for (const int q : qs) {
for (; j0 < j1 && rs[j0] < q; ++j0) below(j0, +1);
for (; rs[j1] < q; ++j0, ++j1) {}
for (; ; ++j1) {
// extinct before rs[j1] ?
int hp = seg.ts[1].mx;
// cerr<<" q = "<<q<<", j1 = "<<j1<<", hp = "<<hp<<endl;
const int pos = above.findRight(q + 1, &NodeSum::test, hp);
// cerr<<" pos = "<<pos<<endl;
if (pos <= rs[j1]) {
exists(q, pos - 1);
break;
}
if (rs[j1] == Q) {
exists(q, Q);
break;
}
below(j1, -1);
}
}
if (u < segN) {
const int mid = (L0 + R0) >> 1;
dfs(u << 1, L0, mid);
dfs(u << 1 | 1, mid, R0);
}
for (const int q : qs) above.change(q, 0);
}
int main() {
for (; ~scanf("%d%d", &N, &Q); ) {
A.resize(N);
for (int i = 0; i < N; ++i) {
scanf("%d", &A[i]);
}
L.resize(Q);
R.resize(Q);
X.resize(Q);
for (int q = 0; q < Q; ++q) {
scanf("%d%d%d", &L[q], &R[q], &X[q]);
--L[q];
}
for (segN = 1; segN < N; segN <<= 1) {}
qss.assign(segN << 1, {});
rss.assign(segN << 1, {});
for (int q = 0; q < Q; ++q) {
int a, b, c, d;
a = c = segN + L[q];
b = d = segN + R[q] - 1;
for (; a <= b; a >>= 1, b >>= 1, c >>= 1, d >>= 1) {
if (a != c) rss[c].push_back(q);
if (b != d) rss[d].push_back(q);
if (a & 1) qss[a++].push_back(q);
if (~b & 1) qss[b--].push_back(q);
}
for (; c; c >>= 1, d >>= 1) {
rss[c].push_back(q);
if (c != d) rss[d].push_back(q);
}
}
above = SegmentTreePoint<NodeSum>(Q);
addss.assign(Q + 1, {});
remss.assign(Q + 1, {});
dfs(1, 0, segN);
const int limX = *max_element(X.begin(), X.end()) + 1;
vector<int> now(limX, 0);
int kind = 0;
for (int q = 0; q < Q; ++q) {
for (const int x : addss[q]) if (!now[x]++) ++kind;
for (const int x : remss[q]) if (!--now[x]) --kind;
printf("%d\n", kind);
}
}
return 0;
}
Details
Tip: Click on the bar to expand more detailed information
Subtask #1:
score: 0
Wrong Answer
Test #1:
score: 0
Wrong Answer
time: 31ms
memory: 6964kb
input:
5000 4999 99 36 47 78 58 58 64 12 42 54 29 56 57 32 99 21 1 6 42 97 82 8 79 92 3 56 19 41 29 59 23 34 76 34 82 20 44 51 60 73 89 65 51 65 15 87 65 70 51 26 40 95 44 62 97 81 43 13 20 81 76 64 47 95 54 56 99 62 91 63 98 58 70 60 47 97 31 74 76 70 10 30 99 33 52 100 14 65 4 6 87 4 8 1 8 87 18 70 76 43...
output:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 10...
result:
wrong answer 2493rd numbers differ - expected: '1934', found: '1933'
Subtask #2:
score: 0
Skipped
Dependency #1:
0%
Subtask #3:
score: 0
Skipped
Dependency #2:
0%
Subtask #4:
score: 0
Skipped
Dependency #3:
0%
Subtask #5:
score: 0
Wrong Answer
Test #5:
score: 0
Wrong Answer
time: 104ms
memory: 20572kb
input:
25000 25000 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 ...
output:
1 2 3 4 5 5 5 3 3 4 4 4 5 4 4 5 6 7 6 6 7 8 9 6 7 7 8 7 8 9 7 8 9 10 8 8 9 10 10 11 12 12 5 6 7 8 9 4 5 6 7 5 6 7 8 6 7 8 7 8 9 10 11 9 10 11 12 12 12 12 9 10 7 8 7 8 8 6 7 8 8 9 9 10 7 8 9 9 9 10 11 10 11 12 12 13 13 14 15 16 15 15 11 4 5 6 7 8 8 9 9 8 9 9 10 11 10 8 8 8 9 9 10 10 10 6 6 7 8 9 4 5 ...
result:
wrong answer 26th numbers differ - expected: '8', found: '7'
Subtask #6:
score: 0
Skipped
Dependency #4:
0%
Subtask #7:
score: 0
Wrong Answer
Test #7:
score: 0
Wrong Answer
time: 177ms
memory: 32028kb
input:
34999 35000 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 2 ...
output:
1 2 3 4 5 6 7 8 9 10 11 12 13 11 7 7 8 9 10 10 11 12 11 12 12 10 9 8 9 4 5 6 7 8 9 10 10 11 12 13 13 14 15 16 17 17 17 16 14 11 11 12 13 14 14 14 14 13 14 14 15 14 15 16 17 18 19 19 19 20 19 16 16 15 15 15 12 13 14 15 16 17 18 19 18 19 19 19 19 17 18 18 19 20 21 21 21 22 18 19 20 20 19 19 19 20 21 2...
result:
wrong answer 26th numbers differ - expected: '11', found: '10'
Subtask #8:
score: 0
Skipped
Dependency #6:
0%
Subtask #9:
score: 0
Wrong Answer
Test #9:
score: 0
Wrong Answer
time: 323ms
memory: 37124kb
input:
45000 45000 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 10 ...
output:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 17 18 19 20 21 22 23 24 24 25 26 27 28 29 29 30 31 30 31 32 31 31 32 32 33 34 34 35 36 37 38 38 39 39 39 38 38 39 40 41 40 41 42 40 40 41 42 43 43 44 45 46 47 48 44 45 44 45 46 45 44 44 45 45 46 47 48 47 48 49 50 51 52 51 51 51 51 50 50 51 52 52 52 52 52 53 ...
result:
wrong answer 92nd numbers differ - expected: '52', found: '51'
Subtask #10:
score: 0
Skipped
Dependency #8:
0%
Subtask #11:
score: 0
Skipped
Dependency #5:
0%
Subtask #12:
score: 0
Skipped
Dependency #11:
0%
Subtask #13:
score: 0
Wrong Answer
Test #13:
score: 0
Wrong Answer
time: 661ms
memory: 47056kb
input:
65000 65000 5 7 8 6 3 6 8 7 2 3 5 10 9 9 4 3 9 1 2 9 1 1 6 10 1 10 5 4 7 1 9 6 6 8 10 5 8 3 2 5 2 3 6 8 7 3 2 3 6 5 1 10 6 2 4 7 8 1 3 3 5 4 2 5 2 5 3 3 6 7 6 9 5 3 10 3 6 2 8 10 9 10 2 5 4 10 3 3 6 3 5 7 141 3 6 3 10 2 7 6 3 5 9 4 10 1 3 9 9 8 2 5 10 1 7 1 8 5 3 3 7 7 9 7 4 1 9 2 2 4 8 6 10 5 7 3 3...
output:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 ...
result:
wrong answer 5810th numbers differ - expected: '5471', found: '5470'
Subtask #14:
score: 0
Skipped
Dependency #12:
0%
Subtask #15:
score: 0
Skipped
Dependency #13:
0%
Subtask #16:
score: 0
Skipped
Dependency #14:
0%
Subtask #17:
score: 0
Skipped
Dependency #16:
0%
Subtask #18:
score: 0
Skipped
Dependency #17:
0%
Subtask #19:
score: 0
Skipped
Dependency #18:
0%
Subtask #20:
score: 0
Skipped
Dependency #19:
0%