模板_Splay Tree

#include<cstdio>
#include<cstdlib>
#include<iostream>
using namespace std;
struct Node{
    Node* ch[2];
    int r,v,s;
    Node(int v):v(v){ch[0]=ch[1]=NULL;r=rand();s=1;}
    bool operator < (const Node &a)const {return r<a.r;}
    int comp(int x){if(x==v) return -1;return x<v?0:1;}
    void maintain(){s=1;if(ch[0]!=NULL) s+=ch[0]->s;if(ch[1]!=NULL) s+=ch[1]->s;}
};

void rotate(Node* &o,int d){
    Node *k=o->ch[d^1];o->ch[d^1]=k->ch[d];k->ch[d]=o;
    o->maintain();k->maintain();o=k;
}
void insert(Node* &o,int x){
    if(o==NULL) o=new Node(x);
    else{
        int d=(x<o->v?0:1);insert(o->ch[d],x);
        if(o->ch[d]->r > o->r) rotate(o,d^1);
    }
    o->maintain();
}
void remove(Node* &o,int x){
    int d=o->comp(x);
    if(d==-1){
        Node *u=o;
        if(o->ch[0]!=NULL&&o->ch[1]!=NULL){
            int d2=(o->ch[0]->r > o->ch[1]->r?1:0);
            rotate(o,d2);remove(o->ch[d2],x);
        }else{
            if(o->ch[0]==NULL) o=o->ch[1];else o=o->ch[0];
            delete u;           
        }
    }
    else remove(o->ch[d],x);
    if(o!=NULL) o->maintain();
}
void splay(Node* &o,int k){//伸展 
    int d=o->comp(k);
    if(d==1) k-=o->ch[0]->s+1;
    if(d!=-1){
        Node *p=o->ch[d];
        int d2=p->comp(k);
        int k2=(d2==0?k:k-p->ch[0]->s-1);
        if(d2!=-1){
            splay(p->ch[d2],k2);
            if(d==d2) rotate(o,d^1);else rotate(o->ch[d],d);
        }
        rotate(o,d^1);
    }
}
Node *merge(Node *left,Node *right){//合并  
    splay(left,left->s);left->ch[1]=right;
    left->maintain();return left;
}
void split(Node *o,int k,Node* &left,Node* &right){//分裂 前K小在left中其余在right中 
    splay(o,k);left=o;right=o->ch[1];
    o->ch[1]=NULL;left->maintain(); 
}
int main(){
    return 0;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值