操作:二叉查找树(插入,查找,删除,dfs序,求最值,第k大/小)
//二叉查找树
//特点:每个点左子树上的点都小于该点,右子树上的点都大于该点
//没有取值相同的点 任意点的左右子树均为二叉查找树
//中序遍历严格单调递增
#include<iostream>
#include<cstdio>
#include<cstring>
#include<cstdlib>
#include<cmath>
#include<algorithm>
using namespace std;
struct uio{
int num,cnt,dfs;//num取值 cnt该取值个数 dfs为dfs序
int l,r;//左右子节点的编号
}bst[1001];
int n,root,ccnt=1,midcnt,ans[1000];//root为最终父节点(根节点) ccnt为输入数据编号 midcnt为中序遍历编号
void get(int x)//插入
{
ccnt++;
int pre=0,now=1;
while(now!=0)
{
if(x==bst[now].num)
{
bst[now].cnt++;
return;
}
if(x<bst[now].num)
{
pre=now;
now=bst[now].l;
}
if(x>bst[now].num)
{
pre=now;
now=bst[now].r;
}
}
bst[ccnt].num=x;
bst[ccnt].cnt=1;
if(x<bst[pre].num)
bst[pre].l=ccnt;
else
bst[pre].r=ccnt;
}
int search(int x)//查找
{
int now=1;
while(now!=0)
{
if(x==bst[now].num)
return now;
if(x<bst[now].num)
now=bst[now].l;
if(x>bst[now].num)
now=bst[now].r;
}
return 0;
}
int getpre(int x)
{
int pre=0,now=1;
while(now!=0)
{
if(x==bst[now].num)
return pre;
if(x<bst[now].num)
{
pre=now;
now=bst[now].l;
}
if(x>bst[now].num)
{
pre=now;
now=bst[now].r;
}
}
return 0;
}
int getnxt(int x)
{
if(bst[x].l==0)
return x;
return getnxt(bst[x].l);
}
void del(int x)//删除
{
int pre=getpre(x);
int now=search(x);
if(bst[now].num>1)
{
bst[now].num--;
return;
}
if(bst[now].l==0&&bst[now].r==0)
{
if(bst[pre].l==now)
bst[pre].l=0;
else
bst[pre].r=0;
}
if(bst[now].l!=0&&bst[now].r==0)
{
bst[pre].l=bst[now].l;
if(bst[pre].r==now)
bst[pre].r=0;
}
if(bst[now].l==0&&bst[now].r!=0)
{
bst[pre].r=bst[now].r;
if(bst[pre].l==now)
bst[pre].l=0;
}
if(bst[now].l!=0&&bst[now].r!=0)
{
int nxt=getnxt(now);
swap(bst[now],bst[nxt]);
del(bst[nxt].num);
}
}
int getmin(int x)//找最小值 返回下标
{
int ans=0,now=1;
while(now!=0)
{
if(bst[now].num<x)
{
ans=now;
now=bst[now].r;
}
else
now=bst[now].l;
}
return ans;
}
int getmax(int x)//找最大值 返回下标
{
int ans=0,now=1;
if(bst[now].num>x)
{
ans=now;
now=bst[now].l;
}
else
now=bst[now].r;
}
int dfsnummin(int x,int y)//dfs序(升序) x起始点编号 y记序
{
if(bst[x].l!=0)
dfsnummin(bst[x].l,y+1);
if(bst[x].r!=0)
dfsnummin(bst[x].r,y+1);
bst[x].dfs=y;
}
int getnokmin(int x,int k)//找第k小
{
dfsnummin(1,1);
int now=1;
while(now!=0)
{
int lsize=0;
int lson=bst[now].l;
int rson=bst[now].r;
if(lson!=0)
lsize=bst[now].dfs;
if(x<=lsize)//x在左子树
now=lson;
else if(lsize+1<=k&&k<=lsize+bst[now].num)//x为当前节点
return now;
else//x在右子树
{
x-=lsize+bst[now].num;
now=rson;
}
}
return 0;
}
int dfsnummax(int x,int y)//dfs序(降序) x起始点编号 y记序
{
if(bst[x].l!=0)
dfsnummax(bst[x].l,y-1);
if(bst[x].r!=0)
dfsnummax(bst[x].r,y-1);
bst[x].dfs=y;
}
int getnokmax(int x,int k)//找第k大
{
dfsnummax(1,n);
int now=1;
while(now!=0)
{
int rsize=0;
int lson=bst[now].l;
int rson=bst[now].r;
if(rson!=0)
rsize=bst[now].dfs;
if(x<=rsize)//x在右子树
now=rson;
else if(rsize+1<=k&&k<=rsize+bst[now].num)//x为当前节点
return now;
else//x在左子树
{
x-=rsize+bst[now].num;
now=rson;
}
}
return 0;
}
void do_something()
{
return;
}
int main()
{
cin>>n>>root;
bst[1].num=root;
bst[1].cnt=1;
for(int i=1;i<=n;i++)
{
int v=0;
cin>>v;
get(v);
}
do_something();
return 0;
}