Getting the tree line into segments update

  • Author: zifeiy
  • Tags: tree line

HDU1698 Just a Hook

#include <bits/stdc++.h>
using namespace std;
#define lson l, m, rt<<1
#define rson m+1, r, rt<<1|1
const int maxn = 100010;
int sum[maxn<<2], lazy[maxn<<2];
inline void push_up(int rt) { sum[rt] = sum[rt<<1] + sum[rt<<1|1]; }
inline void push_down(int rt, int len) {
    if (lazy[rt]) { // 只有在有延迟标记(说明之前全区间覆盖过)才生效
        int l_len = len-len/2, r_len = len/2;
        lazy[rt<<1] = lazy[rt<<1|1] = lazy[rt];
        sum[rt<<1] = l_len * lazy[rt];
        sum[rt<<1|1] = r_len * lazy[rt];
        lazy[rt] = 0;
    }
}
void build(int l, int r, int rt) {
    lazy[rt] = 0;
    if (l == r) {
        sum[rt] = 1;
        return;
    }
    int m = (l + r) >> 1;
    build(lson); build(rson); push_up(rt);
}
void update(int L, int R, int val, int l, int r, int rt) {
    if (L <= l && r <= R) {
        lazy[rt] = val;
        sum[rt] = (r - l + 1) * val;
        return;
    }
    push_down(rt, r-l+1);
    int m = (l + r) >> 1;
    if (L <= m) update(L, R, val, lson);
    if (R > m) update(L, R, val, rson);
    push_up(rt);
}
int T, n, m, a, b, c;
int main() {
    scanf("%d", &T);
    for (int cas = 1; cas <= T; cas ++) {
        scanf("%d%d", &n, &m);
        build(1, n, 1);
        while (m --) {
            scanf("%d%d%d", &a, &b, &c);
            update(a, b, c, 1, n, 1);
        }
        printf("Case %d: The total value of the hook is %d.\n", cas, sum[1]);
    }
    return 0;
}

POJ3468 A Simple Problem with Integers

#include <cstdio>
#define lson l, m, rt<<1
#define rson m+1, r, rt<<1|1
const int maxn = 100010;
long long sum[maxn<<2], lazy[maxn<<2];
inline void push_up(int rt) { sum[rt] = sum[rt<<1] + sum[rt<<1|1]; }
inline void push_down(int rt, int len) {
    if (lazy[rt]) {
        int l_len = len-len/2, r_len = len/2;
        lazy[rt<<1] += lazy[rt];
        lazy[rt<<1|1] += lazy[rt];
        sum[rt<<1] += l_len * lazy[rt];
        sum[rt<<1|1] += r_len * lazy[rt];
        lazy[rt] = 0;
    }
}
void build(int l, int r, int rt) {
    lazy[rt] = 0;
    if (l == r) {
        scanf("%lld", &sum[rt]);
        return;
    }
    int m = (l + r) >> 1;
    build(lson); build(rson); push_up(rt);
}
void update(int L, int R, long long val, int l, int r, int rt) {
    if (L <= l && r <= R) {
        lazy[rt] += val;
        sum[rt] += (r - l + 1) * val;
        return;
    }
    push_down(rt, r-l+1);
    int m = (l + r) >> 1;
    if (L <= m) update(L, R, val, lson);
    if (R > m) update(L, R, val, rson);
    push_up(rt);
}
long long query(int L, int R, int l, int r, int rt) {
    if (L <= l && r <= R) return sum[rt];
    push_down(rt, r-l+1);
    int m = (l + r) >> 1;
    long long res = 0;
    if (L <= m) res += query(L, R, lson);
    if (R > m) res += query(L, R, rson);
    return res;
}
int n, q, a, b, c;
char op[2];
int main() {
    scanf("%d%d", &n, &q);
    build(1, n, 1);
    while (q --) {
        scanf("%s", op);
        if (op[0] == 'C') {
            scanf("%d%d%d", &a, &b, &c);
            update(a, b, c, 1, n, 1);
        } else {
            scanf("%d%d", &a, &b);
            printf("%lld\n", query(a, b, 1, n, 1));
        }
    }
    return 0;
}

POJ2528 Mayor's posters

Topic links: http://poj.org/problem?id=2528
subject to the effect: to give you an infinitely long board, and then in turn attached to the top of the n high poster, ask you finally can see how many posters.
Ideas Analysis: tree line interval update problem, but be careful, be very large to the length, there 1e9, not addressed directly maintain a segment tree will certainly MLE, TLE, but we note that only a maximum total of points 2e4, therefore we can use discrete ideological pretreatment prior to the interval.
But pay attention to the simple discretization error may occur, given the following two simple examples should be able to reflect ordinary discrete defects:
Example 1: 1-10 1-4 5-10
Example 2: 1-10 1-4 6-10
After general have become a discrete [1,4][1,2][3,4]
segment covers 2 [1,2], line 3 covers up [3,4], then the segment 1 is completely overwritten it?
examples of First off completely covered, and the two examples are not covered by
the solution is greater than the distance between two adjacent points 1, then insert a middle point, this question Lazy mark also uses the idea of
direct child node does not update first section marked for processing, then mark down if you need to update downstream layer.
Codes are as follows (my code directly to the value stored in the delay in the mark):

#include <cstdio>
#include <algorithm>
using namespace std;
#define lson l, m, rt<<1
#define rson m+1, r, rt<<1|1
const int maxn = 100010;
long long lazy[maxn<<2];
inline void push_down(int rt, int len) {
    if (lazy[rt]) {
        int l_len = len-len/2, r_len = len/2;
        lazy[rt<<1] = lazy[rt<<1|1] = lazy[rt];
        lazy[rt] = 0;
    }
}
void build(int l, int r, int rt) {
    lazy[rt] = 0;
    if (l == r) return;
    int m = (l + r) >> 1;
    build(lson); build(rson);
}
void update(int L, int R, int val, int l, int r, int rt) {
    if (L <= l && r <= R) {
        lazy[rt] = val;
        return;
    }
    push_down(rt, r-l+1);
    int m = (l + r) >> 1;
    if (L <= m) update(L, R, val, lson);
    if (R > m) update(L, R, val, rson);
}
int ans;
bool vis[maxn];
void query(int l, int r, int rt) {
    if (l == r || lazy[rt]) {
        if (lazy[rt] && !vis[ lazy[rt] ]) { vis[ lazy[rt] ] = true; ans ++; }
        return;
    }
    int m = (l + r) >> 1;
    query(lson); query(rson);
}
int T, n, l[maxn], r[maxn], num[maxn], mp[10000010], sz, cnt;
int main() {
    scanf("%d", &T);
    while (T --) {
        scanf("%d", &n);
        cnt = ans = 0;
        for (int i = 1; i <= n; i ++) vis[i] = false;
        for (int i = 1; i <= n; i ++) {
            scanf("%d%d", &l[i], &r[i]);
            num[cnt++] = l[i];
            num[cnt++] = r[i];
        }
        sort(num, num+cnt);
        cnt = unique(num, num+cnt) - num;
        sz = 0;
        for (int i = 0; i < cnt; i ++) {
            if (i > 0 && num[i-1]+1 < num[i]) mp[ num[i]-1 ] = sz ++;
            mp[ num[i] ] = sz ++;
        }
        build(0, sz-1, 1);
        for (int i = 1; i <= n; i ++) {
            int lnum = mp[ l[i] ];
            int rnum = mp[ r[i] ];
            update(lnum, rnum, i, 0, sz-1, 1);
        }
        query(0, sz-1, 1);
        printf("%d\n", ans);
    }
    return 0;
}

POJ3225 range

Topic links: http://poj.org/problem?id=3225 this question a Chinese face problems.
Title effect: operation section, intersection, and complement the like.
Ideas:
we have to analyze the operation:

  • U: The interval \ ([l, r] \ ) covers into 1;
  • I: The interval \ ((- \ infty, L) \) , \ ((R & lt, + \ infty) \) cover to 0;
  • D: The interval \ ([l, r] \ ) cover to 0;
  • C: The interval \ ((- \ infty, L) \) , \ ((R & lt, + \ infty) \) cover to 0, and the interval \ ([L, R & lt] \) 0/1 interchangeable;
  • S: The interval \ ([L, R & lt] \) 0/1 interchanged.

Operations into segments covered is very simple, more special is that exchange zone 0/1 this operation, we can call the XOR operation.

For lazy Tags:

  • Overlay mark: We 0 or 1 to indicate whether 1 or 0 are included within the range, the above period by -1 represents i.e. contains 1 also contains 0;
  • Or exclusive flag: whether the XOR operation.

Nature: When a range is covered, whether or not previously XOR mark no sense.
Therefore, when a node needs to obtain the overlay mark or marker exclusive emptied;
and when a node obtained exclusive or labeled, first sentence overlay marks, if it is 0 or 1, a change of coverage directly labeled, or otherwise change the exclusive tag.

Open interval number is multiplied by 2 as long as it can be handled (even indicate the endpoints for the odd representing the interval between the end points)

Tree line features:

  • update: Update into segments, segment or isobutyl;
  • query: simple hash

Code: Slightly.

Exercise

Guess you like

Origin www.cnblogs.com/codedecision/p/11687527.html