POJ-3667 线段树(区间合并)

#include <cstring>
#include <cstdio>
#include <iostream>
#include <algorithm>
using namespace std;

#define lson l,m,rt<<1
#define rson m+1,r,rt<<1|1
#define INF 1000001000

const int maxn = 100100;
int sum[maxn<<2],lsum[maxn<<2],rsum[maxn<<2],col[maxn<<2];
void build(int l,int r,int rt){
col[rt]=-1;
sum[rt]=lsum[rt]=rsum[rt]=r-l+1;
if(l==r) return ;
int m=(l+r)>>1;
build(lson);
build(rson);
}

void pushdown(int l,int r,int rt){
if(col[rt]!=-1){
    int m=(l+r)>>1;
    col[rt<<1]=col[rt<<1|1]=col[rt];
    if(col[rt]){
        sum[rt<<1]=lsum[rt<<1]=rsum[rt<<1]=0;
        sum[rt<<1|1]=lsum[rt<<1|1]=rsum[rt<<1|1]=0;
    }
    else{
        sum[rt<<1]=lsum[rt<<1]=rsum[rt<<1]=m-l+1;
        sum[rt<<1|1]=lsum[rt<<1|1]=rsum[rt<<1|1]=r-m;
    }
    col[rt]=-1;
}
}

void pushup(int l,int r,int rt){
int m=(l+r)>>1;

sum[rt]=max(sum[rt<<1],sum[rt<<1|1]);
sum[rt]=max(sum[rt],rsum[rt<<1]+lsum[rt<<1|1]);

lsum[rt]=lsum[rt<<1];
if(lsum[rt]==m-l+1) lsum[rt]+=lsum[rt<<1|1];

rsum[rt]=rsum[rt<<1|1];
if(rsum[rt]==r-m) rsum[rt]+=rsum[rt<<1];
}

//check_out
int ql,qr,val;
void  update(int l,int r,int rt){
if(ql<=l&&r<=qr){
    col[rt]=val;
    if(val){ sum[rt]=lsum[rt]=rsum[rt]=0; }
    else   { sum[rt]=lsum[rt]=rsum[rt]=r-l+1; }
    return ;
}
pushdown(l,r,rt);
int m=(l+r)>>1;
if(ql<=m) update(lson);
if(qr> m) update(rson);
pushup(l,r,rt);
}

int width,ans;
void query(int l,int r,int rt){
//cout<<l<<" "<<r<<" "<<endl;
if(l==r){
    ans=l; return ;
}
pushdown(l,r,rt);
int m=(l+r)>>1;
int ok1=0,ok2=0;
if(sum[rt<<1]>=width) ok1=1;
if(sum[rt<<1|1]>=width) ok2=1;
if(ok1){
    query(lson);
}
else if(!ok1&&!ok2){
    ans= m-rsum[rt<<1]+1;
}
else {
    if(rsum[rt<<1]+lsum[rt<<1|1]>=width){
        ans= m-rsum[rt<<1]+1;
    }
    else {
        query(rson);
    }
}
}

int n,Q;
int main()
{
   while(scanf("%d %d",&n,&Q)==2){
   build(1,n,1);
   while(Q--){
    int cmd;
    scanf("%d",&cmd);
    if(cmd==1){
        scanf("%d",&width);
        if(sum[1]>=width){
           query(1,n,1);
           printf("%d\n",ans);
           ql=ans; qr=ans+width-1; val=1;
           update(1,n,1);
        }
        else printf("0\n");
    }
    else {
        int d;
        scanf("%d %d",&ql,&d);
        qr=ql+d-1; val=0;
        update(1,n,1);
    }
    //cout<<sum[1]<<endl;
   }
   }
return 0;
}


你可能感兴趣的:(Algorithm,C++,算法,poj)