您的位置:首页 > 其它

hdu 1540 && poj 2892

2013-07-18 13:24 399 查看
题目

D 指将改点更新为0

Q 查询改点处左右两端的连续区间

R 将前一个D的点回复成1

典型的区间合并的题目,代码:

#include<iostream>
#include<cstdio>

using namespace std;
#define maxn  50005
#define lson l,m,rt<<1
#define rson m+1,r,rt<<1|1

struct Tree
{
    int l,r;
    int lsum,rsum,msum;
}tree[maxn<<2];

inline void PushUp(int rt)
{
    tree[rt].lsum=tree[rt<<1].lsum;
    tree[rt].rsum=tree[rt<<1|1].rsum;
    if(tree[rt<<1].lsum==tree[rt<<1].r-tree[rt<<1].l+1)
       tree[rt].lsum+=tree[rt<<1|1].lsum;
    if(tree[rt<<1|1].rsum==tree[rt<<1|1].r-tree[rt<<1|1].l+1)
       tree[rt].rsum+=tree[rt<<1].rsum;
    tree[rt].msum=max(tree[rt<<1].rsum+tree[rt<<1|1].lsum,max(tree[rt<<1].msum,tree[rt<<1|1].msum));
}

inline void build(int l,int r,int rt)
{
    tree[rt].l=l;
    tree[rt].r=r;
    tree[rt].lsum=tree[rt].rsum=tree[rt].msum=r-l+1;
    if(l==r) return ;
    int m=(l+r)>>1;
    build(lson);
    build(rson);
}

inline void update(int pos,int val,int rt)
{
    int l,r;
    l=tree[rt].l;
    r=tree[rt].r;
    if(l==r){
        tree[rt].lsum=tree[rt].rsum=tree[rt].msum=val?1:0;
        return ;
    }
    int m=(l+r)>>1;
    if(pos<=m) update(pos,val,rt<<1);
    else update(pos,val,rt<<1|1);
    PushUp(rt);
}

inline int query(int pos,int rt)
{
    int l,r;
    l=tree[rt].l;
    r=tree[rt].r;
    if(l==r||(tree[rt].msum==0||tree[rt].msum==r-l+1)){
        return tree[rt].msum;
    }
    int m=(l+r)>>1;
    if(pos<=m){
        if(pos>=tree[rt<<1].r-tree[rt<<1].rsum+1)
            return query(pos,rt<<1)+query(m+1,rt<<1|1);
        else return query(pos,rt<<1);
    }
    else{
        if(pos<=tree[rt<<1|1].l+tree[rt<<1|1].lsum-1)
            return query(pos,rt<<1|1)+query(m,rt<<1);
        else return query(pos,rt<<1|1);
    }
}

int que[maxn];
int top;

int main()
{
    int n,m;
    char str[10];
    int a;
    while(~scanf("%d%d",&n,&m)){
        build(1,n,1);
        while(m--){
            scanf("%s",str);
            if(str[0]=='D'){
                scanf("%d",&a);
                que[top++]=a;
                update(a,0,1);
            }
            else if(str[0]=='Q'){
                scanf("%d",&a);
                printf("%d\n",query(a,1));
            }
            else{
                a=que[--top];
                update(a,1,1);
            }
        }
    }
    return 0;
}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: