• POJ--2528 Mayor's posters (线段树)


    题目链接:POJ--2528 Mayor's posters

    题目大意:给你一个无限长的板子,然后依次往上面贴n张等高的海报,问你最后能看到多少张海报。

    思路分析:线段树区间更新问题,但是要注意,给的长度的可能非常大,有1e9,不加处理直接维护一个线段树肯定会

    MLE,TLE,但是我们注意到一共最多只有2e4个点,因此我们可以用离散化的思想先对区间进行预处理,所谓的离散化,

    在我理解看来就是将一个很大的区间映射为一个很小的区间,而不改变原有的大小覆盖关系,但是注意简单的离散化可能

    会出现错误,给出下面两个简单的例子应该能体现普通离散化的缺陷:
    例子一:1-10 1-4 5-10
    例子二:1-10 1-4 6-10
    普通离散化后都变成了[1,4][1,2][3,4]
    线段2覆盖了[1,2],线段3覆盖了[3,4],那么线段1是否被完全覆盖掉了呢?
    例子一是完全被覆盖掉了,而例子二没有被覆盖

    解决的办法则是对于距离大于1的两相邻点,中间再插入一个点,本题还用到了Lazy标记的思想

    直接更新区间进行标记而先不对子节点进行处理,如果需要往下更新再将标记下传一层。

    #include<iostream>
    #include<cstring>
    #include<algorithm>
    #include<vector>
    using namespace std;
    #define maxn 100010
    #define LL long long
    int a[maxn*4],ll[maxn],rr[maxn],lz[maxn*4];
    bool fa[maxn*4];
    vector<int>q;
    int ans;
    void init(){
      memset(a,-1,sizeof(a));
      memset(ll,0,sizeof(ll));
      memset(rr,0,sizeof(rr));
      memset(fa,0,sizeof(fa));
      q.clear();ans=0;
    }
    int getid(int x){
       return lower_bound(q.begin(),q.end(),x)-q.begin()+1;
    }
    void lazy(int in){
       if(a[in]>0){
           a[in*2]=a[in];
           a[in*2+1]=a[in];
           a[in]=-1;
       }
    }
    void updata(int l,int r,int x,int y,int in,int va){
       if(l==x&&r==y){
          a[in]=va;
          return ;
       }
       lazy(in);
       int mid=(l+r)/2;
       if(y<=mid){
          updata(l,mid,x,y,in*2,va);
       }else if(x>mid){
          updata(mid+1,r,x,y,in*2+1,va);
       }else{
          updata(l,mid,x,mid,in*2,va);
          updata(mid+1,r,mid+1,y,in*2+1,va);
       }
    
    }
    void query(int l,int r,int in){
       //cout<<a[in]<<endl;
       if(a[in]>0){
           if(!fa[a[in]]){
              fa[a[in]]=1;
              ans++;
           }
           return ;
       }
       if(l==r) return ;
       int mid=(l+r)/2;
       query(l,mid,in*2);
       query(mid+1,r,in*2+1);
    
    }
    int main(){
       int t;
       cin>>t;
       while(t--){
          init();
          int n,mx=0;
          cin>>n;
          for(int j=1;j<=m;j++){
             cin>>ll[j]>>rr[j];
             q.push_back(ll[j]);
             q.push_back(rr[j]);
          }
          sort(q.begin(),q.end());
    
          q.erase(unique(q.begin(),q.end()),q.end());
          int z=q.size();
          for(int j=1;j<z;j++){
             if(q[j]-q[j-1]>1){
                 q.push_back(q[j-1]+1);
             }
          }
          sort(q.begin(),q.end());
          mx=q.size();
          for(int j=1;j<=m;j++){
             int l=getid(ll[j]);
             int r=getid(rr[j]);
             updata(1,mx,l,r,1,j);
          }
          query(1,mx,1);
          cout<<ans<<endl;
       }
    }
  • 相关阅读:
    关于Response.End的亦常
    关于web.config
    本地打印机的设置
    xml的操作
    javascript定义对象的几种简单方法
    WindowsXP下共享无线网络设置步骤
    第四章:使用Rich控件
    第五章母版页
    第八章数据访问概述
    对lock(obj)中的obj的理解
  • 原文地址:https://www.cnblogs.com/Dvelpro/p/9897872.html
Copyright © 2020-2023  润新知