Number of Minimums on a Segment,Wrong answer on test 12,求 Hack,thx.
#include <bits/stdc++.h>
std::vector<int> a, min, cnt;
int ls(int p) { return (p << 1) + 1; }
int rs(int p) { return (p << 1) + 2; }
void build(int l, int r, int p = 0) {
if (l == r) {
min.at(p) = a.at(l);
cnt.at(p) = 1;
} else {
const int mid = l + r >> 1;
build(l, mid, ls(p));
build(mid + 1, r, rs(p));
const int lm = min.at(ls(p)), rm = min.at(rs(p));
if (lm == rm) {
min.at(p) = lm;
cnt.at(p) = cnt.at(ls(p)) + cnt.at(rs(p));
} else if (lm < rm) {
min.at(p) = lm;
cnt.at(p) = cnt.at(ls(p));
} else {
min.at(p) = rm;
cnt.at(p) = cnt.at(rs(p));
}
}
}
int mfind(int l, int r, int pl, int pr, int p = 0) {
if (l <= pl && r >= pr)
return min.at(p);
const int mid = pl + pr >> 1;
if (l <= mid && r > mid)
return std::min(mfind(l, r, pl, mid, ls(p)), mfind(l, r, mid + 1, pr, rs(p)));
else if (l <= mid)
return mfind(l, r, pl, mid, ls(p));
else
return mfind(l, r, mid + 1, pr, rs(p));
}
int cfind(int l, int r, int pl, int pr, int p = 0) {
if (l <= pl && r >= pr)
return cnt.at(p);
const int mid = pl + pr >> 1;
if (l <= mid && r > mid)
return cfind(l, r, pl, mid, ls(p)) + cfind(l, r, mid + 1, pr, rs(p));
else if (l <= mid)
return cfind(l, r, pl, mid, ls(p));
else
return cfind(l, r, mid + 1, pr, rs(p));
}
void modify(int idx, int v, int pl, int pr, int p = 0) {
if (pl == pr) {
a.at(idx) = v;
min.at(p) = v;
} else {
int mid = pl + pr >> 1;
if (idx <= mid)
modify(idx, v, pl, mid, ls(p));
else
modify(idx, v, mid + 1, pr, rs(p));
const int lm = min.at(ls(p)), rm = min.at(rs(p));
if (lm == rm) {
min.at(p) = lm;
cnt.at(p) = cnt.at(ls(p)) + cnt.at(rs(p));
} else if (lm < rm) {
min.at(p) = lm;
cnt.at(p) = cnt.at(ls(p));
} else {
min.at(p) = rm;
cnt.at(p) = cnt.at(rs(p));
}
}
}
int main() {
std::ios::sync_with_stdio(false);
std::cin.tie(nullptr);
int n, m;
std::cin >> n >> m;
a.resize(n);
min.resize(n << 2);
cnt.resize(n << 2);
for (int &v : a)
std::cin >> v;
build(0, n - 1);
while (m--) {
int tp, x, y;
std::cin >> tp >> x >> y;
if (tp == 1)
modify(x, y, 0, n - 1);
else
std::cout << mfind(x, y - 1, 0, n - 1) << ' ' << cfind(x, y - 1, 0, n - 1) << '\n';
}
return 0;
}