• Luogu P3369 【模板】普通平衡树


    解法

    就是最普通的splay啦,直接放代码QAQ

    代码

    #include<iostream>
    #include<algorithm>
    #include<cstring>
    #include<cstdio>
    #include<cmath>
    #define INF 0x3f3f3f3f
    using namespace std;
    typedef long long LL;
    const int N=1e5+5;
    
    int read()
    {
    	int x=0,p=1; char ch=getchar();
    	while((ch<'0'||ch>'9')&&ch!='-') ch=getchar();
    	if(ch=='-') p=-1,ch=getchar();
    	while(ch>='0'&&ch<='9') x=(x<<3)+(x<<1)+ch-'0',ch=getchar();
    	return x*p;
    }
    
    int ch[N][2],par[N],val[N],cnt[N],siz[N],tot,root;
    
    int chk(int x) { return ch[par[x]][1]==x; }
    
    void pushup(int x) { siz[x]=siz[ch[x][0]]+siz[ch[x][1]]+cnt[x]; }
    
    int rotate(int x)
    {
    	int y=par[x],z=par[y],k=chk(x),w=ch[x][k^1];
    	ch[z][chk(y)]=x,par[x]=z;
    	ch[y][k]=w,par[w]=y;
    	ch[x][k^1]=y,par[y]=x;
    	pushup(y),pushup(x);
    }
    
    void splay(int x,int goal)
    {
    	int y,z;
    	while(par[x]!=goal)
    	{
    		y=par[x],z=par[y];
    		if(z!=goal)
    			chk(x)==chk(y) ? rotate(y):rotate(x);
    		rotate(x);
    	}
    	if(!goal) root=x;
    }
    
    void find(int x)
    {
    	int u=root;
    	while(ch[u][x>val[u]] && x!=val[u]) 
    		u=ch[u][x>val[u]];
    	splay(u,0);
    }
    
    void insert(int x)
    {
    	int u=root,p=0;
    	while(u && val[u]!=x) p=u,u=ch[u][x>val[u]];
    	if(u) cnt[u]++;
    	else 
    	{
    		u=++tot;
    		if(p) ch[p][x>val[p]]=u;
    		ch[u][0]=ch[u][1]=0;
    		par[u]=p; val[u]=x;
    		cnt[u]=siz[u]=1;
    	}
    	splay(u,0);
    }
    
    int kth(int k)
    {
    	int u=root;
    	if(k>siz[u]) return 0;
    	for(; ;)
    	{
    		if(ch[u][0] && k<=siz[ch[u][0]])
    			u=ch[u][0];
    		else if(k>siz[ch[u][0]]+cnt[u])
    			k-=siz[ch[u][0]]+cnt[u],u=ch[u][1];
    			 else 
    			 	return u;
    	}
    }
    	
    int Next(int x,int f)
    {
    	find(x);
    	int u=root;
    	if(val[u]>x && f) return u;
    	if(val[u]<x && !f) return u;
    	u=ch[u][f];
    	while(ch[u][f^1]) u=ch[u][f^1];
    	return u;
    }
    
    void remove(int x)
    {
    	int last=Next(x,0),next=Next(x,1);
    	splay(last,0),splay(next,last);
    	int del=ch[next][0];
    	if(cnt[del]>1)
    		cnt[del]--,splay(del,0);
    	else 
    		ch[next][0]=0,pushup(next),pushup(root);
    }
    
    int main()		
    {
    	int n,op,x; 
    	n=read();
    	insert(INF);
    	insert(-INF);
    	while(n--)
    	{
    		op=read(),x=read();
    		switch (op)
    		{
    			case 1: insert(x); break ;
    			case 2: remove(x); break ;
    			case 3: find(x); printf("%d
    ",siz[ch[root][0]]); break ;
    			case 4: printf("%d
    ",val[kth(x+1)]); break ;
    			case 5: printf("%d
    ",val[Next(x,0)]); break ;
    			case 6: printf("%d
    ",val[Next(x,1)]); break ;
    		}
    	}
        return 0;
    }
    
  • 相关阅读:
    js获取html参数。
    jquery判断单选按钮是否选中
    js滑动触屏事件监听
    单例模式之Java
    Android开发把项目打包成apk
    jdom解析XML 中文
    PhoneGap Connection
    java 文件操作
    html参数编码
    JS 判断字符串包含
  • 原文地址:https://www.cnblogs.com/lzqlalala/p/10958820.html
Copyright © 2020-2023  润新知