[LOJ # 3033. "JOISC 2019 Day2" two antennas

LOJ # 3033. "JOISC 2019 Day2" two antennas

Updated front of the antenna with the back of the antenna, the maximum value of the tree line version of history saved

That is the maximum segment tree need to maintain historical versions of the tag antenna behind the largest and the smallest one, the smallest usable range of values ​​antenna, antenna interval the maximum available value

\ (I \) may be \ (J \) is used, then the \ (J \) in \ ([i + A_ {i }, i + B_ {i}] \) , the right end point when we enumerate if to \ (i + A_ {i} \) put \ (I \) marked as available if to \ (i + B_ {i} + 1 \) put \ (I \) marked as unavailable

Then enumerate the right end, to add a new endpoint is now in the segment tree interval \ ([i - B_ {i }, i- A_ {i}] \) is available, so we need to mark the section marked

Then ask for a corresponding right to the point, just need to find the maximum interval version of history like

#include <bits/stdc++.h>
#define fi first
#define se second
#define pii pair<int,int>
#define mp make_pair
#define pb push_back
#define space putchar(' ')
#define enter putchar('\n')
#define eps 1e-10
#define MAXN 200005
#define ba 47
//#define ivorysi
using namespace std;
typedef long long int64;
typedef unsigned int u32;
typedef double db;
template<class T>
void read(T &res) {
    res = 0;T f = 1;char c = getchar();
    while(c < '0' || c > '9') {
    if(c == '-') f = -1;
    c = getchar();
    }
    while(c >= '0' && c <= '9') {
    res = res * 10 +c - '0';
    c = getchar();
    }
    res *= f;
}
template<class T>
void out(T x) {
    if(x < 0) {x = -x;putchar('-');}
    if(x >= 10) {
    out(x / 10);
    }
    putchar('0' + x % 10);
}
struct node {
    int l,r,mn,mx,lzmn,lzmx,oldmx;
}tr[MAXN * 4];
int N,Q,H[MAXN],A[MAXN],B[MAXN],ans[MAXN];
int ql[MAXN],qr[MAXN];
vector<int> ed[MAXN],st[MAXN],qe[MAXN];
void update(int u) {
    tr[u].mn = min(tr[u << 1].mn,tr[u << 1 | 1].mn);
    tr[u].mx = max(tr[u << 1].mx,tr[u << 1 | 1].mx);
    tr[u].oldmx = max(tr[u << 1].oldmx,tr[u << 1 | 1].oldmx);
}
void addlz(int u,int v) {
    tr[u].oldmx = max(tr[u].oldmx,v - tr[u].mn);
    tr[u].oldmx = max(tr[u].oldmx,tr[u].mx - v);
    tr[u].lzmn = min(v,tr[u].lzmn);
    tr[u].lzmx = max(v,tr[u].lzmx);
}
void pushdown(int u) {
    if(tr[u].lzmn <= 1e9) {
    addlz(u << 1,tr[u].lzmn);
    addlz(u << 1 | 1,tr[u].lzmn);
    tr[u].lzmn = 2e9;
    }
    if(tr[u].lzmx > 0) {
    addlz(u << 1,tr[u].lzmx);
    addlz(u << 1 | 1,tr[u].lzmx);
    tr[u].lzmx = 0;
    }
}
void build(int u,int l,int r) {
    tr[u].l = l;tr[u].r = r;
    tr[u].mn = 1e9 + 1,tr[u].mx = 0;
    tr[u].lzmn = 2e9;tr[u].lzmx = 0;tr[u].oldmx = -1;
    if(l == r) return;
    int mid = (l + r) >> 1;
    build(u << 1,l,mid);
    build(u << 1 | 1,mid + 1,r);    
}
void change(int u,int pos,int op) {
    if(tr[u].l == tr[u].r) {
    if(op == 1) tr[u].mn = tr[u].mx = H[pos];
    else {
        tr[u].mn = 1e9 + 1,tr[u].mx = 0;
    }
    return;
    }
    pushdown(u);
    int mid = (tr[u].l + tr[u].r) >> 1;
    if(pos <= mid) change(u << 1,pos,op);
    else if(pos > mid) change(u << 1 | 1,pos,op);
    update(u);
}
void add(int u,int l,int r,int v) {
    if(tr[u].l == l && tr[u].r == r) {
    addlz(u,v);return;
    }
    pushdown(u);
    int mid = (tr[u].l + tr[u].r) >> 1;
    if(r <= mid) add(u << 1,l,r,v);
    else if(l > mid) add(u << 1 | 1,l,r,v);
    else {add(u << 1,l,mid,v);add(u << 1 | 1,mid + 1,r,v);}
    update(u);
}
int Query(int u,int l,int r) {
    if(tr[u].l == l && tr[u].r == r) return tr[u].oldmx;
    int mid = (tr[u].l + tr[u].r) >> 1;
    pushdown(u);
    if(r <= mid) return Query(u << 1,l,r);
    else if(l > mid) return Query(u << 1 | 1,l,r);
    else {return max(Query(u << 1,l,mid),Query(u << 1 | 1,mid + 1,r));}
}
void Solve() {
    read(N);
    for(int i = 1 ; i <= N ; ++i) {
    read(H[i]);read(A[i]);read(B[i]);
    int l = i + A[i],r = min(i + B[i],N);
    if(l <= r) {st[l].pb(i),ed[r + 1].pb(i);}
    }
    read(Q);
    for(int i = 1 ; i <= Q ; ++i) {
    read(ql[i]);read(qr[i]);
    qe[qr[i]].pb(i);
    }
    build(1,1,N);
    for(int i = 1 ; i <= N ; ++i) {
    for(auto t : st[i]) change(1,t,1);
    for(auto t : ed[i]) change(1,t,-1);
    int l = i - B[i],r = i - A[i];
    l = max(l,1);
    if(l <= r) add(1,l,r,H[i]);
    for(auto id : qe[i]) {
        ans[id] = Query(1,ql[id],qr[id]);
    }
    }
    for(int i = 1 ; i <= Q ; ++i) {
    out(ans[i]);enter;
    }
}
int main() {
#ifdef ivorysi
    freopen("f1.in","r",stdin);
#endif
    Solve();
}

Guess you like

Origin www.cnblogs.com/ivorysi/p/10948370.html