# [BZOJ2006][[NOI2010]超级钢琴][优先队列+线段树]

#### 思路：

(i,L+i1,Min(R+i1,n))

(i,L,x1),(i,x+1,R)

#### 代码：

#include <bits/stdc++.h>
const int Maxn = 500010;
using namespace std;
inline char get(void) {
static char buf[1000000], *p1 = buf, *p2 = buf;
if (p1 == p2) {
p2 = (p1 = buf) + fread(buf, 1, 1000000, stdin);
if (p1 == p2) return EOF;
}
return *p1++;
}
x = 0; static char c; bool minus = false;
for (; !(c >= '0' && c <= '9'); c = get()) if (c == '-') minus = true;
for (; c >= '0' && c <= '9'; x = x * 10 + c - '0', c = get()); if (minus) x = -x;
}
int a[Maxn];
long long ans;
struct H {
#define c(x) const int &x
int m, w, l, ll, rl;
H(void) {}
H(c(m), c(w), c(l), c(ll), c(rl)) : m(m), w(w), l(l), ll(ll), rl(rl) {}
friend bool operator < (const H &a, const H &b) {
return a.m < b.m;
}
} x;
priority_queue<H> qu;
struct S {
int m, w;
S(void) { m = -(1 << 30); }
friend bool operator > (const S &a, const S &b) {
return a.m > b.m;
}
} tmp;
S t[Maxn << 2];
inline S Max(const S &a, const S &b) {
return a > b ? a : b;
}
inline int Min(const int &a, const int &b) {
return a < b ? a : b;
}
inline void build(int o, int l, int r) {
if (l == r) {
t[o].m = a[l];
t[o].w = l;
return;
}
int mid = (l + r) >> 1;
build(o << 1, l, mid);
build(o << 1 | 1, mid + 1, r);
t[o] = Max(t[o << 1], t[o << 1 | 1]);
}
inline S ask(int o, int l, int r, int L, int R) {
if (l >= L && r <= R) return t[o];
int mid = (l + r) >> 1; S a1, a2;
if (mid >= L) a1 = ask(o << 1, l, mid, L, R);
if (mid < R) a2 = ask(o << 1 | 1, mid + 1, r, L, R);
return Max(a1, a2);
}
int n, k, l, r;
int main(void) {
//freopen("in.txt", "r", stdin);
//freopen("out.txt", "w", stdout);
for (int i = 1; i <= n; i++) {
a[i] += a[i - 1];
}
build(1, 1, n);
int ll, rr;
for (int i = 0; i < n - l + 1; i++) {
ll = i + l, rr = Min(i + r, n);
tmp = ask(1, 1, n, ll, rr);
qu.push(H(tmp.m - a[i], tmp.w, i + 1, ll, rr));
}
while (k--) {
x = qu.top(); qu.pop();
ans += x.m;
if (x.w - 1 >= x.ll) {
tmp = ask(1, 1, n, x.ll, x.w - 1);
qu.push(H(tmp.m - a[x.l - 1], tmp.w, x.l, x.ll, x.w - 1));
}
if (x.w + 1 <= x.rl) {
tmp = ask(1, 1, n, x.w + 1, x.rl);
qu.push(H(tmp.m - a[x.l - 1], tmp.w, x.l, x.w + 1, x.rl));
}
}
printf("%lld", ans);
return 0

By g1n0st