zoukankan      html  css  js  c++  java
  • BZOJ 3600 替罪羊树+线段树

    思路:
    当然是抄的黄学长的题解啦

    //By SiriusRen
    #include <cstdio>
    #include <algorithm>
    using namespace std;
    #define N 500005
    int n,m,rt,R,top,id[N],mx[N],pos[N];
    double a[N];char ch[11];
    struct data{
        int l,r;
        friend bool operator>(data x,data y){
            if(a[x.l]>a[y.l])return 1;
            if(a[x.l]==a[y.l]&&a[x.r]>a[y.r])return 1;
            return 0;
        }
        friend bool operator==(data x,data y){
            if(x.l!=y.l||x.r!=y.r)return 0;
            return 1;
        }
    };
    struct SCTree{
        int cnt,size[N],ls[N],rs[N];data v[N];
        void dfs(int k){
            if(!k)return;
            dfs(ls[k]);
            id[++top]=k;
            dfs(rs[k]);
        }
        void build(int &k,int l,int r,double lv,double rv){
            if(l>r){k=0;return;}
            double mv=(lv+rv)/2.0;
            int mid=(l+r)>>1;k=id[mid];a[k]=mv;
            build(ls[k],l,mid-1,lv,mv);
            build(rs[k],mid+1,r,mv,rv);
            size[k]=size[ls[k]]+size[rs[k]]+1;
        }
        void rebuild(int &k,double lv,double rv){
            top=0;dfs(k);
            build(k,1,top,lv,rv);
        }
        int insert(int &k,double lv,double rv,data val){
            double mv=(lv+rv)/2.0;
            if(!k){
                k=++cnt;a[k]=mv;v[k]=val,size[k]=1;
                return k;
            }
            int p;
            if(val==v[k])return k;
            else{
                size[k]++;
                if(val>v[k])p=insert(rs[k],mv,rv,val);
                else p=insert(ls[k],lv,mv,val);
            }
            if(size[k]*0.666>max(size[ls[k]],size[rs[k]])){
                if(R){
                    if(ls[k]==R)rebuild(ls[k],lv,mv);
                    else rebuild(rs[k],mv,rv);
                    R=0;
                }
            }
            else R=k;
            return p;
        }
    }sc;
    void modify(int k,int l,int r,int v){
        int mid=(l+r)>>1;
        if(l==r){mx[k]=l;return;}
        if(v<=mid)modify(k<<1,l,mid,v);
        else modify(k<<1|1,mid+1,r,v);
        int x=mx[k<<1],y=mx[k<<1|1];
        mx[k]=a[pos[x]]>=a[pos[y]]?x:y;
    }
    int query(int k,int l,int r,int x,int y){
        if(l>=x&&r<=y)return mx[k];
        int mid=(l+r)>>1;
        if(mid<x)return query(k<<1|1,mid+1,r,x,y);
        else if(mid>=y)return query(k<<1,l,mid,x,y);
        else{
            int p1=query(k<<1|1,mid+1,r,x,y),p2=query(k<<1,l,mid,x,y);
            return a[pos[p1]]>a[pos[p2]]?p1:p2;
        }
    }
    int main(){
        scanf("%d%d",&n,&m);
        a[0]=-1;
        sc.insert(rt,0,1,(data){0,0});
        for(int i=1;i<=n;i++)pos[i]=1;
        for(int i=1;i<=n;i++)modify(1,1,n,i);
        int l,r,K;
        for(int i=1;i<=m;i++){
            scanf("%s%d%d",ch+1,&l,&r);
            if(ch[1]=='C'){
                scanf("%d",&K);
                pos[K]=sc.insert(rt,0,1,(data){pos[l],pos[r]});
                if(R)sc.rebuild(rt,0,1),R=0;
                modify(1,1,n,K);
            }
            else printf("%d
    ",query(1,1,n,l,r));
        }
    }

    这里写图片描述

  • 相关阅读:
    慎用静态类static class
    20170617
    学习笔记之工厂模式-2017年1月11日23:00:53
    链表翻转
    面试被虐
    tips
    依赖注入那些事儿
    浅谈算法和数据结构(1):栈和队列
    猫都能学会的Unity3D Shader入门指南(一)
    SerializeField等Unity内的小用法
  • 原文地址:https://www.cnblogs.com/SiriusRen/p/6532125.html
Copyright © 2011-2022 走看看