zoukankan      html  css  js  c++  java
  • Educational Codeforces Round 36 (Rated for Div. 2) E. Physical Education Lessons

    提供两种思路
    一种线段树区间更新
    另一种用map维护连续的区间,也是题解的思路
    第二种很难写(我太渣,看了别人的代码,发现自己写的太烦了)

    #include<iostream>
    #include<map>
    #include<iostream>
    #include<cstring>
    #include<cstdio>
    #include<set>
    #include<vector>
    #include<queue>
    #include<stack>
    #include<cmath>
    #include<algorithm>
    using namespace std;
    typedef long long ll;
    const int INF = 0x3f3f3f3f;
    const int N = 6e5+5;
    #define MS(x,y) memset(x,y,sizeof(x))
    #define MP(x, y) make_pair(x, y)
    #define lson l, m, rt<<1
    #define rson m+1, r, rt<<1|1
    
    int main() {
        int n, q;
        while(~scanf("%d %d", &n, &q)) {
            map<int, int> mp;
            mp[-1] = -1;
            mp[1] = n;
            mp[n+1] = INF;
    
            int ans = n;
            while(q --) {
                int l, r, k; 
    
    
                scanf("%d %d %d", &l, &r, &k);  
                int tt = r;
                if(k == 2 && r != n) tt = r+1;
    
                auto it = mp.upper_bound(l);
                auto it2 = mp.upper_bound(tt);
                it --; it2 --;
    
                int head1 = it -> first;  int len1 = it -> second;
                int head2 = it2 -> first;  int len2 = it2 -> second;
    
                while(1){
                    int flag = 0;
                    if(it == it2) flag = 1;
                    ans -= it->second;
                    auto tmp = it;  
                //  if(it->first == n+1) while(1);
                    it ++;
            //      printf("erase: %d
    ", tmp->first);
                    mp.erase(tmp);
                    if(flag) break;
                }
            //for(auto i = mp.begin(); i != mp.end(); ++i) printf("%d:%d ", i->first, i->second); printf("
    ");
            //  printf("%d %d %d %d %d %d
    ", head1, len1, head2, len2, l, r);
    
                if(k == 1) {
                    if(head1 + len1 - 1 >= l && l!=head1) {
                        mp[head1] = l - head1;
                        ans += l - head1;
                    } else if(l != head1){
                        mp[head1] = len1; 
                        ans += len1;
                    }
    
                    if(head2 + len2 - 1 > r) {
                        mp[r+1] = head2 + len2 - 1 - r;
                        ans += head2 + len2 - 1 - r;
                    }           
                } else {
                    int L = l; int R = max(r, head2 + len2 -1);
                    if(head1 + len1 < l) { 
                        mp[head1] = len1;
                        ans += len1;
                    }else L = head1;
    
                    mp[L] = R-L+1;
                    ans += R-L+1;
                }
    
    
    
        //      for(auto i = mp.begin(); i != mp.end(); ++i) printf("%d:%d ", i->first, i->second); printf("
    ");
    
                printf("%d
    ", ans);
            }
        }
        return 0;
    }
    #include<iostream>
    #include<map>
    #include<iostream>
    #include<cstring>
    #include<cstdio>
    #include<set>
    #include<vector>
    #include<queue>
    #include<stack>
    #include<cmath>
    #include<algorithm>
    using namespace std;
    typedef long long ll;
    const int INF = 0x3f3f3f3f;
    const int N = 6e5+5;
    #define MS(x,y) memset(x,y,sizeof(x))
    #define MP(x, y) make_pair(x, y)
    #define lson l, m, rt<<1
    #define rson m+1, r, rt<<1|1
    
    
    int Q[N][3];
    int has[N * 2]; int cnt;
    
    int sum[N << 2];
    int lazy[N << 2];
    
    void build(int l, int r, int rt) {
        lazy[rt] = 0;
        sum[rt] = has[r] - has[l-1];
        if(l == r) {
            return;
        }
        int m = (l + r) >> 1;
        build(lson); build(rson);
    }
    void update(int ty, int L, int R, int l, int r, int rt) {
        //printf("%d %d
    ", l, r);
        if(L <= has[l-1]+1 && has[r] <= R) {
            lazy[rt] = ty == 1? -1 : 1;
            sum[rt] = ty == 1? 0 : has[r] - has[l-1];
            return;
        }
    
    
        int m = (l + r) >> 1;
    
        if(lazy[rt] == 1) {
            lazy[rt<<1] = 1; sum[rt<<1] = has[m] - has[l-1];
            lazy[rt<<1|1] = 1; sum[rt<<1|1] = has[r] - has[m]; 
            lazy[rt] = 0;
        } else if(lazy[rt] == -1){
            lazy[rt<<1] = -1; sum[rt<<1] = 0;
            lazy[rt<<1|1] = -1; sum[rt<<1|1] = 0;
            lazy[rt] = 0;
        }
    
        if(L <= has[m-1]+1) update(ty, L, R, lson);
        if(R > has[m])  update(ty, L, R, rson);
        sum[rt] = sum[rt<<1] + sum[rt<<1|1];
    }
    void debug(int l, int r, int rt) {
        printf("%d %d %d
    ", l, r, sum[rt]);
        if(l == r) return;
        int m = (l + r) >> 1;
        debug(lson);
        debug(rson);
    }
    int main() {
        int n;
        while(~scanf("%d", &n)) {
            cnt = 0;
    
            int q; scanf("%d", &q);
            for(int i = 0; i < q; ++i) {
                scanf("%d %d %d", &Q[i][0], &Q[i][1], &Q[i][2]);
                has[cnt ++] = Q[i][0] - 1; 
                has[cnt ++] = Q[i][1];
            }
            has[cnt ++] = 0;
            has[cnt ++] = n;
    
            sort(has, has+cnt);
            cnt = unique(has, has + cnt) - has;
    //      for(int i = 0; i < cnt; ++i) printf("%d ", has[i]); printf("
    ");
    
    
            build(1, cnt-1, 1);
        //` debug(1, cnt-1, 1);
            for(int i = 0; i < q; ++i) {
                update(Q[i][2], Q[i][0], Q[i][1], 1, cnt-1, 1);
                printf("%d
    ", sum[1]); 
        //      debug(1, cnt-1, 1);
            }
    
        }
        return 0;
    }
    
    
  • 相关阅读:
    APB协议
    AHB总线协议(一)
    C++内存机制中内存溢出、内存泄露、内存越界和栈溢出的区别和联系
    深入理解C++内存管理机制
    c/c++内存机制(一)(转)
    与临时对象的斗争(下)
    与临时对象的斗争(上)ZZ
    C++异常处理解析: 异常的引发(throw), 捕获(try catch)、异常安全
    qt5信息提示框QMessageBox用法
    红黑树
  • 原文地址:https://www.cnblogs.com/Basasuya/p/8433682.html
Copyright © 2011-2022 走看看