zoukankan      html  css  js  c++  java
  • POJ2528 Mayor's posters(线段树+离散化)

    题意 : 在墙上贴海报, n(n<=10000)个人依次贴海报,给出每张海报所贴的范围li,ri(1<=li<=ri<=10000000)。求出最后还能看见多少张海报。

    分析 : 很容易想到利用线段树来成段置换,最后统计总区间不同数的个数。但是这里有一个问题,就是区间可以很大,线段树开不了那么大的空间,遂想能不能离散化。实际上只记录坐标的相对大小进行离散化最后是不影响我们计算的,但是光是普通的离散化是不行的,就是我们贴海报的实际意义是对(l, r)段进行添加,而不是对于这个区间的点进行添加,是段树不是点树,如果这样普通离散化的话就会出现一个问题,比如数据1-10、1-4、6-10 行的,我们离散化后是1-4、1-2、3-4 ,不离散的结果是 3 但是离散化后再计算就是 2 了!原因就是我们是成段更新而不是点更新,进行添加海报的(l, r)的意义是对这一段进行添加,而离散化之后将原本不相邻的点变成了相邻的点,就导致了上面例子 4 - 6被覆盖了!解决这个问题的方法就是,在离散化的时候,将原本不相邻的两个点中间添加一个数,来表示中间是有“缝隙”的。

    AC代码:

    #include <cstdio>
    
    #include <cstring>
    
    #include <algorithm>
    
    using namespace std;
    
    #define lson l , m , rt << 1
    
    #define rson m + 1 , r , rt << 1 | 1
    const int maxn =  21112;
    bool hash[maxn];
    int li[maxn] , ri[maxn];
    int X[maxn<<3];
    int col[maxn<<4];
    int cnt;
    
    void PushDown(int rt) {
    
             if (col[rt] != -1) {
    
                     col[rt<<1] = col[rt<<1|1] = col[rt];
    
                     col[rt] = -1;
    
             }
    
    }
    void update(int L,int R,int c,int l,int r,int rt) {
    
             if (L <= l && r <= R) {
    
                     col[rt] = c;
    
                     return ;
    
             }
             PushDown(rt);
    
             int m = (l + r) >> 1;
    
             if (L <= m) update(L , R , c , lson);
    
             if (m < R) update(L , R , c , rson);
    
    }
    
    void query(int l,int r,int rt) {
    
             if (col[rt] != -1) {
    
                     if (!hash[col[rt]]) cnt ++;
    
                     hash[ col[rt] ] = true;
    
                     return ;
             }
             if (l == r) return ;
             int m = (l + r) >> 1;
             query(lson);
             query(rson);
    
    }
    int Bin(int key,int n,int X[]) {
    
             int l = 0 , r = n - 1;
    
             while (l <= r) {
    
                     int m = (l + r) >> 1;
    
                     if (X[m] == key) return m;
    
                     if (X[m] < key) l = m + 1;
    
                     else r = m - 1;
    
             }
    
             return -1;
    
    }
    
    int main() {
    
             int T , n;
    
             scanf("%d",&T);
    
             while (T --) {
              // memset (col,0,sizeof(col));
                     scanf("%d",&n);
    
                     int nn = 0;
    
                     for (int i = 0 ; i < n ; i ++) {
    
                              scanf("%d%d",&li[i] , &ri[i]);
                              X[nn++] = li[i];///记录所有出现的点
                              X[nn++] = ri[i];
    
                     }
                     sort(X , X + nn);
                     int m = unique(X,X+nn)-X;///去重
                     ///在不相邻的点中间添加一个数
                     for (int i = m - 1 ; i > 0 ; i --) {
                              if (X[i] != X[i-1] + 1) X[m ++] = X[i-1] + 1;
    
                     }
                     sort(X , X + m);
                     memset(col , -1 , sizeof(col));
                     for (int i = 0 ; i < n ; i ++) {
                              int l = lower_bound(X,X+m,li[i])-X;////在离散化之后的坐标系arr中寻找左端点
                              int r = lower_bound(X,X+m,ri[i])-X;
                              //   int l = Bin(li[i] , m , X);
                              //int r = Bin(ri[i] , m , X);
                              update(l , r , i , 0 , m , 1);
                     }
                     cnt = 0;
                     memset(hash , false , sizeof(hash));
                     query(0 , m , 1);
                     printf("%d
    ",cnt);
    
             }
    
             return 0;
    
    }
    View Code
  • 相关阅读:
    leetcode35. search Insert Position
    leetcode26.Remove Duplicates from Sorted Array
    leetcode46.Permutation & leetcode47.Permutation II
    leetcode.5 Longest Palindromic Substring
    [转载] C++中new和malloc的区别
    [转载] C++中的自由存储区和堆
    xCode8以及iOS10 的新特性
    cell上添加倒计时,以及时差问题的解决
    cell的复用机制
    iOS 懒加载模式
  • 原文地址:https://www.cnblogs.com/shuaihui520/p/9094129.html
Copyright © 2011-2022 走看看