【线段树求LCIS】HDU 3308

来源:互联网 发布:数据恢复精灵离线激活 编辑:程序博客网 时间:2024/05/22 03:58

注意查询时当左右两个区间可以合并的情况min(mid-x+1, t[id<<1].rm) + min(y-mid, t[id<<1|1].lm)

#define N 100005struct node{    int l,r;    int lm,rm;    int mx;}t[N*4+1000];int a[N+100];inline void up(int id){    t[id].lm = t[id<<1].lm;    if(t[id<<1].lm == t[id<<1].r-t[id<<1].l+1 && a[t[id<<1].r] < a[t[id<<1|1].l]){        t[id].lm += t[id<<1|1].lm;    }    t[id].rm = t[id<<1|1].rm;    if(t[id<<1|1].rm == t[id<<1|1].r-t[id<<1|1].l+1 && a[t[id<<1].r] < a[t[id<<1|1].l]){        t[id].rm += t[id<<1].rm;    }    t[id].mx = 0;    if(a[t[id<<1].r] < a[t[id<<1|1].l]){        t[id].mx = t[id<<1].rm + t[id<<1|1].lm;    }    t[id].mx = max(t[id].mx,max(t[id<<1].mx,t[id<<1|1].mx));//这里wa死了!!!}void build(int l,int r,int id){    t[id].l = l;    t[id].r = r;    if(l == r){        t[id].lm = 1;//left        t[id].rm = 1;//right        t[id].mx = 1;//max        return ;    }    int mid = (l+r)>>1;    build(l,mid,id<<1);    build(mid+1,r,id<<1|1);    up(id);}void update(int id,int pos,int val){    if(t[id].l == pos && t[id].r == pos){        a[pos] = val;        return ;    }    int l = t[id].l;    int r = t[id].r;    int mid = (l+r)>>1;    if(pos<=mid)update(id<<1,pos,val);    else if(pos>mid)update(id<<1|1,pos,val);    up(id);}int ask(int id,int x,int y){    if(t[id].l == x && t[id].r == y){        return t[id].mx;    }    if(t[id].l<t[id].r){        int mid = (t[id].l + t[id].r) >> 1;        if(y<=mid)return ask(id<<1,x,y);        else if(x>mid)return ask(id<<1|1,x,y);        else {            if(a[mid]<a[mid+1]){                int tmp = min(mid-x+1, t[id<<1].rm) + min(y-mid, t[id<<1|1].lm);//注意这里!明白!                return max(tmp,max(ask(id<<1,x,mid),ask(id<<1|1,mid+1,y)));            }            return max(ask(id<<1,x,mid),ask(id<<1|1,mid+1,y));        }    }}int main(){    int ca;    scanf("%d",&ca);    while(ca--){        int n,m;        scanf("%d%d",&n,&m);        int i,j;        for(i=1;i<=n;i++)scanf("%d",&a[i]);        build(1,n,1);        while(m--){            char str[3];            int x,y;            scanf("%s%d%d",str,&x,&y);            if(str[0] == 'U'){                x++;                update(1,x,y);            } else {                x++,y++;                int ans = ask(1,x,y);                printf("%d\n",ans);            }        }    }    return 0;}


















原创粉丝点击