DZY Loves Sorting HDU - 5649

http://acm.hdu.edu.cn/showproblem.php?pid=5649

二分答案记为lim 将小于等于lim的数置为1 其余置为0 这样就可以处理排序操作 最后判一下目标位置处是否为1即可

二分的值越大 整个区间内的1数量越多 每次排序操作都会把1全部挪到左边或右边 1越多越有可能覆盖到目标位置 具有单调性

#include <bits/stdc++.h>
using namespace std;
const int maxn=1e5+10;

struct node
{
    int tp,l,r;
};

node order[maxn];
int sum[4*maxn],laz[4*maxn];
int ary[maxn];
int n,q,pos;

void change(int l,int r,int val,int cur)
{
    sum[cur]=val*(r-l+1);
    laz[cur]=val;
}

void pushup(int cur)
{
    sum[cur]=sum[2*cur]+sum[2*cur+1];
}

void pushdown(int l,int r,int cur)
{
    int m;
    m=(l+r)/2;
    if(laz[cur]!=-1){
        change(l,m,laz[cur],2*cur);
        change(m+1,r,laz[cur],2*cur+1);
        laz[cur]=-1;
    }
}

void build(int l,int r,int cur,int val)
{
    int m;
    laz[cur]=-1;
    if(l==r){
        if(ary[l]<=val) sum[cur]=1;
        else sum[cur]=0;
        return;
    }
    m=(l+r)/2;
    build(l,m,2*cur,val);
    build(m+1,r,2*cur+1,val);
    pushup(cur);
}

int query(int pl,int pr,int l,int r,int cur)
{
    int res,m;
    if(pl<=l&&r<=pr){
        return sum[cur];
    }
    pushdown(l,r,cur);
    res=0,m=(l+r)/2;
    if(pl<=m) res+=query(pl,pr,l,m,2*cur);
    if(pr>m) res+=query(pl,pr,m+1,r,2*cur+1);
    return res;
}

void update(int pl,int pr,int val,int l,int r,int cur)
{
    int m;
    if(pl<=l&&r<=pr){
        change(l,r,val,cur);
        return;
    }
    pushdown(l,r,cur);
    m=(l+r)/2;
    if(pl<=m) update(pl,pr,val,l,m,2*cur);
    if(pr>m) update(pl,pr,val,m+1,r,2*cur+1);
    pushup(cur);
}

bool judge(int lim)
{
    int res,i,j;
    //printf("***%d***\n",lim);
    build(1,n,1,lim);
    /*
    for(i=1;i<=n;i++){
        printf("%d ",query(i,i,1,n,1));
    }
    printf("\n");
    */
    for(i=1;i<=q;i++){
        if(order[i].tp==0){
            res=query(order[i].l,order[i].r,1,n,1);
            if(res>0) update(order[i].l,order[i].l+res-1,1,1,n,1);
            update(order[i].l+res,order[i].r,0,1,n,1);
        }
        else{
            res=query(order[i].l,order[i].r,1,n,1);
            res=order[i].r-order[i].l+1-res;
            if(res>0) update(order[i].l,order[i].l+res-1,0,1,n,1);
            update(order[i].l+res,order[i].r,1,1,n,1);
        }
        /*
        for(j=1;j<=n;j++){
            printf("%d ",query(j,j,1,n,1));
        }
        printf("\n");
        */
    }
    //printf("\n");
    res=query(pos,pos,1,n,1);
    return res;
}

int main()
{
    int t,i,l,r,m,ans;
    scanf("%d",&t);
    while(t--){
        scanf("%d%d",&n,&q);
        for(i=1;i<=n;i++){
            scanf("%d",&ary[i]);
        }
        for(i=1;i<=q;i++){
            scanf("%d%d%d",&order[i].tp,&order[i].l,&order[i].r);
        }
        scanf("%d",&pos);
        l=1,r=n;
        while(l<=r){
            m=(l+r)/2;
            if(judge(m)) r=m-1,ans=m;
            else l=m+1;
        }
        printf("%d\n",ans);
    }
    return 0;
}

猜你喜欢

转载自blog.csdn.net/sunyutian1998/article/details/88994852