Codeforces 815D Karen and Cards segment tree || inclusion and exclusion (see explanations)

Karen and Cards

Just start thinking of inclusion and exclusion, but the feeling is not very good inclusion and exclusion, gun and then went to see the solution of the problem. .

Enumeration we consider a, n rows into two sheets> = a and <a, then we point as the two-dimensional plane, which points will be considered

Limits for> = a card, the restricted area by subtracting the upper right corner of the rectangular region as a whole, for <a, the card, the restricted area

Bottom left rectangle that defines f (b) a second maximum value of the c-bit b restricted, first discovered the function f is monotonic, a card <transition to a> = a well from modification,

So we enumerate descending with a tree line to statistics in the answer.

 

Inclusion-exclusion, then you can look at this. .

https://codeforces.com/contest/815/submission/27860187

Feeling a little clever.

#include<bits/stdc++.h>
#define LL long long
#define LD long double
#define ull unsigned long long
#define fi first
#define se second
#define mk make_pair
#define PLL pair<LL, LL>
#define PLI pair<LL, int>
#define PII pair<int, int>
#define SZ(x) ((int)x.size())
#define ALL(x) (x).begin(), (x).end()
#define fio ios::sync_with_stdio(false); cin.tie(0);

using namespace std;

const int N = 5e5 + 7;
const int inf = 0x3f3f3f3f;
const LL INF = 0x3f3f3f3f3f3f3f3f;
const int mod = 998244353;
const double eps = 1e-8;
const double PI = acos(-1);

template<class T, class S> inline void add(T& a, S b) {a += b; if(a >= mod) a -= mod;}
template<class T, class S> inline void sub(T& a, S b) {a -= b; if(a < 0) a += mod;}
template<class T, class S> inline bool chkmax(T& a, S b) {return a < b ? a = b, true : false;}
template<class T, class S> inline bool chkmin(T& a, S b) {return a > b ? a = b, true : false;}

int n, p, q, r;
int a[N], b[N], c[N];
int id[N], limit[N];
LL ans;

#define lson l, mid, rt << 1
#define rson mid + 1, r, rt << 1 | 1
struct segmentTree {
    LL sum[N << 2]; int lazy[N << 2], mn[N << 2], mx[N << 2];
    inline void pull(int rt) {
        sum[rt] = sum[rt << 1] + sum[rt << 1 | 1];
        mx[rt] = max(mx[rt << 1], mx[rt << 1 | 1]);
        mn[rt] = min(mn[rt << 1], mn[rt << 1 | 1]);
    }
    inline void push(int rt, int l, int r) {
        if(~lazy[rt]) {
            int mid = l + r >> 1;
            sum[rt << 1] = 1LL * (mid - l + 1) * lazy[rt];
            sum[rt << 1 | 1] = 1LL * (r - mid) * lazy[rt];
            lazy[rt << 1] = lazy[rt << 1 | 1] = lazy[rt];
            mx[rt << 1] = mn[rt << 1] = lazy[rt];
            mx[rt << 1 | 1] = mn[rt << 1 | 1] = lazy[rt];
            lazy[rt] = -1;
        }
    }
    void build(int l, int r, int rt) {
        lazy[rt] = -1;
        if(l == r) {
            sum[rt] = limit[l];
            mx[rt] = limit[l];
            mn[rt] = limit[l];
            return;
        }
        int mid = l + r >> 1;
        build(lson); build(rson);
        pull(rt);
    }
    void update(int L, int R, int val, int l, int r, int rt) {
        if(R < l || r < L || R < L) return;
        if(mn[rt] >= val) return;
        if(L <= l && r <= R && mx[rt] <= val) {
            sum[rt] = 1LL * (r - l + 1) * val;
            mx[rt] = val;
            mn[rt] = val;
            lazy[rt] = val;
            return;
        }
        if(l == r) return;
        push(rt, l, r);
        int mid = l + r >> 1;
        update(L, R, val, lson);
        update (L, R, val, rson);
        pull(rt);
    }
} Tree;


int main () {
    scanf("%d%d%d%d", &n, &p, &q, &r);
    for(int i = 1; i <= n; i++) {
        scanf("%d%d%d", &a[i], &b[i], &c[i]);
        id[i] = i;
    }
    sort(id + 1, id + 1 + n, [&](int x, int y) {
        return a[x] > a[y];
    });
    for(int i = 1; i <= n; i++) chkmax(limit[b[i]], c[i]);
    for(int i = q; i >= 1; i--) chkmax(limit[i], limit[i + 1]);
    Tree.build(1, q, 1);
    for(int i = p, j = 1; i >= 1; i--) {
        while(j <= n && a[id[j]] >= i) {
            Tree.update(1, b[id[j]], r, 1, q, 1);
            Tree.update(b[id[j]] + 1, q, c[id[j]], 1, q, 1);
            j++;
        }
        ans += 1LL * q * r - Tree.sum[1];
    }
    printf("%lld\n", ans);
    return 0;
}

/*
*/

 

Guess you like

Origin www.cnblogs.com/CJLHY/p/11039180.html