BZOJ P3224 LOJ P104 普通平衡树【Splay板子】

嗯没错就是一个平衡树的板子,然而就是这个板子我调了一下午没有调出来最后还是麻烦了CJQ大佬花了一晚上帮我调试。

感谢!

参考代码:

#include <cmath>
#include <cstdio>
#include <cstring>
#include <iostream>
#include <algorithm>
#define SG string
#define DB double
using namespace std;
const int Max=2e5+5;
int N,Ans;
int Cnt=1,Root,Fa[Max],Key[Max],Num[Max],Size[Max],CH[Max][2];
inline int Read(){
    int X=0;char CH=getchar();bool F=0;
    while(CH>'9'||CH<'0'){if(CH=='-')F=1;CH=getchar();}
    while(CH>='0'&&CH<='9'){X=(X<<1)+(X<<3)+CH-'0';CH=getchar();}
    return F?-X:X;
}
inline void Write(int X){
    if(X<0)X=-X,putchar('-');
    if(X>9)Write(X/10);
    putchar(X%10+48);
}
int NewNode(int _Key,int _Fa){
    Key[++Cnt]=_Key;Fa[Cnt]=_Fa;
    Num[Cnt]=Size[Cnt]=1;CH[Cnt][0]=CH[Cnt][1]=0;
    return Cnt;
}
void PushUp(int X){
    Size[X]=Size[CH[X][0]]+Size[CH[X][1]]+Num[X];
}
void Rotate(int X,int P){
    int Y=Fa[X];
    CH[Y][!P]=CH[X][P];
    Fa[CH[X][P]]=Y;Fa[X]=Fa[Y];
    if(Fa[X]){
        CH[Fa[X]][CH[Fa[X]][1]==Y]=X;
    }CH[X][P]=Y;Fa[Y]=X;
    PushUp(Y);PushUp(X);
}
void Splay(int X,int To){
    while(Fa[X]!=To){
        if(Fa[Fa[X]]==To){
            Rotate(X,CH[Fa[X]][0]==X);
        } else {
            int Y=Fa[X],Z=Fa[Y];
            int P=(CH[Z][0]==Y);
            if(CH[Y][P]==X){
                Rotate(X,!P),Rotate(X,P);
            } else {
                Rotate(Y,P),Rotate(X,P);
            }
        }
    }
    if(To==0){
        Root=X;
    }
}
int Find(int _Key){
    if(!Root){
        return 0;
    }
    int X=Root;
    while(X){
        if(Key[X]==_Key){
            break;
        }X=CH[X][_Key>Key[X]];
    }
    if(X){
        Splay(X,0);
    }
    return X;
}
void Insert(int _Key){
    if(!Root){
        Root=NewNode(_Key,0);
    } else {
        int X=Root,Y=0;
        while(X){
            Y=X;
            if(Key[X]==_Key){
                Num[X]++;
                Size[X]++;
                break;
            }Size[X]++;
            X=CH[X][_Key>Key[X]];
        }
        if(!X){
            X=CH[Y][_Key>Key[Y]]=NewNode(_Key,Y);
        }Splay(X,0);
    }
}
void Delete(int _Key){
    int X=Find(_Key);
    if(!X){
        return ;
    }
    if(Num[X]>1){
        Num[X]--;
        PushUp(X);return;
    }
    int Y=CH[X][0];
    while(CH[Y][1]){
        Y=CH[Y][1];
    }
    int Z=CH[X][1];
    while(CH[Z][0]){
        Z=CH[Z][0];
    }
    if(!Y&&!Z){
        Root=0;return;
    }
    if(!Y){
        Splay(Z,0);
        CH[Z][0]=0;PushUp(Z);return ;
    }
    if(!Z){
        Splay(Y,0);
        CH[Y][1]=0;PushUp(Y);return ;
    }
    Splay(Y,0);Splay(Z,Y);
    CH[Z][0]=0;PushUp(Z);PushUp(Y);
}
int GetRank(int K,int _Key){
    if(K==0){
        return 0;
    }
    if(_Key==Key[K]){
        return Size[CH[K][0]]+1;
    } else if (_Key>Key[K]){
        return Size[CH[K][0]]+Num[K]+GetRank(CH[K][1],_Key); 
    } else {
        return GetRank(CH[K][0],_Key);
    }

} 
int GetKth(int K){
    if(!Root||K>Size[Root]){
        return 0;
    }
    int X=Root;
    while(X){
        if(K>=Size[CH[X][0]]+1&&K<=Size[CH[X][0]]+Num[X]){
            break;
        }
        if(K>Size[CH[X][0]]+Num[X]){
            K-=(Size[CH[X][0]]+Num[X]);
            X=CH[X][1];
        } else {
            X=CH[X][0];
        }
    }
    Splay(X,0);
    return Key[X];
}
int Pre(int _Key){ 
    Insert(_Key); 
    int X=CH[Root][0];
    while(CH[X][1]){
        X=CH[X][1];
    }Splay(X,0);
    Delete(_Key);
    return Key[X];
}
int Suc(int _Key){
    Insert(_Key);
    int X=CH[Root][1];
    while(CH[X][0]){
        X=CH[X][0];
    }
    Splay(X,0);
    Delete(_Key);
    return Key[X];
}
int main(){
    int I,J,K;
    N=Read();
    for(I=1;I<=N;I++){
        int X=Read(),Y=Read();
        if(X==1){
            Insert(Y);
        } else if (X==2){
            Delete(Y);
        } else if (X==3){
            Write(GetRank(Root,Y)),putchar('\n');
        } else if (X==4){
            Write(GetKth(Y)),putchar('\n');
        } else if (X==5){
            Write(Pre(Y)),putchar('\n');
        } 
        else {
            Write(Suc(Y)),putchar('\n');
        }
    }
    return 0;
}

猜你喜欢

转载自blog.csdn.net/yanzhenhuai/article/details/81091273
今日推荐