• bzoj4552


    二分在q位置上的数。其他数若大于它,则为1,否则为0,最后若该位上的数为0,则区间右移l,否则左移r

    check过程中用线段树维护,降序升序可以用区间复制实现

    #include<cstdio>
    #include<cctype>
    #include<algorithm>
    using namespace std;
    const int N=100005;
    int n,m,q,tr[4*N],laz[4*N],a[N],typ[N],ql[N],qr[N],val[N];
    
    inline int read(){
        char ch=getchar();int k=0,f=1;
        while(!isdigit(ch)){if(ch=='-')f=-1;ch=getchar();}
        while(isdigit(ch)){k=(k<<1)+(k<<3)+ch-'0';ch=getchar();}
        return k*f;
    }
    
    void buildtr(int now,int l,int r){
        laz[now]=0;
        if(l==r){tr[now]=val[l];return;}
        int mid=(l+r)>>1;
        buildtr(now<<1,l,mid);buildtr(now<<1|1,mid+1,r);
        tr[now]=tr[now<<1]+tr[now<<1|1];
    }
    
    void pushdown(int now,int l,int r){
        if(laz[now]==0)return;
        int mid=(l+r)>>1;
        if(laz[now]==1){
            laz[now<<1]=laz[now<<1|1]=1;laz[now]=0;
            tr[now<<1]=mid-l+1;tr[now<<1|1]=r-mid;
        }else
        if(laz[now]==-1){
            laz[now<<1]=laz[now<<1|1]=-1;laz[now]=0;
            tr[now<<1]=tr[now<<1|1]=0;
        }
    }
    
    void change(int now,int l,int r,int L,int R,int v){
        if(l>=L&&r<=R){
            if(v==1){laz[now]=1;tr[now]=r-l+1;}else{laz[now]=-1;tr[now]=0;}
            return;
        }
        pushdown(now,l,r);
        int mid=(l+r)>>1;
        if(mid>=L)change(now<<1,l,mid,L,R,v);
        if(mid<R)change(now<<1|1,mid+1,r,L,R,v);
        tr[now]=tr[now<<1]+tr[now<<1|1];
    }
    
    int query(int now,int l,int r,int L,int R){
        if(l>=L&&r<=R)return tr[now];
        pushdown(now,l,r);
        int mid=(l+r)>>1,res=0;
        if(mid>=L)res+=query(now<<1,l,mid,L,R);
        if(mid<R)res+=query(now<<1|1,mid+1,r,L,R);
        return res;
    }
    
    void Putans(int x){
        if(x>=10)Putans(x/10);putchar(x%10+'0');
    }
    
    int main(){
        n=read();m=read();
        for(int i=1;i<=n;i++)a[i]=read();
        for(int i=1;i<=m;i++){typ[i]=read();ql[i]=read();qr[i]=read();if(ql[i]>qr[i])swap(ql[i],qr[i]);}
        q=read();
        int l=1,r=n;
        while(l<r){
            int mid=(l+r)>>1;
            for(int i=1;i<=n;i++)val[i]=a[i]>mid?1:0;
            buildtr(1,1,n);
            for(int i=1;i<=m;i++){
                int cnt=query(1,1,n,ql[i],qr[i]);
                if(typ[i]==0){
                    if(cnt>0&&cnt<qr[i]-ql[i]+1)change(1,1,n,qr[i]-cnt+1,qr[i],1);
                    if(qr[i]-cnt>=ql[i]&&cnt>0)change(1,1,n,ql[i],qr[i]-cnt,0);
                }
                else{
                    if(cnt>0&&cnt<qr[i]-ql[i]+1)change(1,1,n,ql[i],ql[i]+cnt-1,1);
                    if(ql[i]+cnt<=qr[i]&&cnt>0)change(1,1,n,ql[i]+cnt,qr[i],0);
                }
            }
            if(query(1,1,n,q,q))l=mid+1;else r=mid;
        }
        Putans(l);
    }
  • 相关阅读:
    python中获取当前位置所在的行号和函数名(转)
    Scrapy 轻松定制网络爬虫(转)
    XPath教程
    Scrapy入门教程(转)
    django safe 过滤器--不对字符串进行转义(转)
    WinDbg-如何抓取dump文件
    Windows系统默认调试器设置
    javascript(js)自动刷新页面的实现方法总结
    [HTML]不让TD中的文本撑开表格(转)
    apache 与 iis共存
  • 原文地址:https://www.cnblogs.com/MikuKnight/p/8888413.html
Copyright © 2020-2023  润新知