返回目录
题意
构建一颗AVL树(平衡二叉排序树)。
样例(可复制)
5
88 70 61 96 120
//output
70
7
88 70 61 96 120 90 65
//output
88
注意点
- 本题难度较大,如果PAT考试的时候实在做不出来,可以直接输出中位数,7个测试点可以过5个,取得17分
- AVL树(平衡二叉排序树)需要满足:①是二叉排序树,即树的每个节点的左子树上所有节点都小于该节点,每个节点的右子树上所有节点都大于该节点②每个节点的左高度与右高度的差的绝对值不能超过1
- 平衡二叉树构建过程中,会出现4种需要旋转的情况:LL,LR,RR,RL。每种情况需要左旋或右旋看下面的参考代码。在手写模拟中,我们常用交换的方式,但实际代码里面,我们直接赋值即可。
直接中位数(17分)
#include<bits/stdc++.h>
using namespace std;
int main(){
int n,data[25];
cin>>n;
for(int i=0;i<n;i++)scanf("%d",&data[i]);
sort(data,data+n);
printf("%d",data[n/2]);
return 0;
}
AVL
#include<bits/stdc++.h>
using namespace std;
struct node{
int v,height;
node *lc,*rc;
}*root;
node* newnode(int v){
node* no=new node;
no->v=v;
no->height=1;
no->lc=no->rc=NULL;
return no;
}
int getheight(node* root){
if(root==NULL)return 0;
return root->height;
}
int getbalancenum(node* root){
return getheight(root->lc)-getheight(root->rc);
}
void L(node* &root){
node* tmp=root->rc;//tmp为新的root
root->rc=tmp->lc;//把tmp->rc裁剪下来
tmp->lc=root;
//只有root和tmp的高度发生了变化
root->height=max(getheight(root->lc),getheight(root->rc))+1;
tmp->height=max(getheight(tmp->lc),getheight(tmp->rc))+1;
root=tmp;
}
void R(node* &root){
node* tmp=root->lc;
root->lc=tmp->rc;
tmp->rc=root;
root->height=max(getheight(root->lc),getheight(root->rc))+1;
tmp->height=max(getheight(tmp->lc),getheight(tmp->rc))+1;
root=tmp;
}
void insert(node* &root,int v){
if(root==NULL){
root=newnode(v);
return;
}
if(v<root->v){
insert(root->lc,v);
root->height=max(getheight(root->lc),getheight(root->rc))+1;
if(getbalancenum(root)==2){
if(getbalancenum(root->lc)==1){//LL型
R(root);//右旋
}else if(getbalancenum(root->lc)==-1){//LR型
L(root->lc);//先左旋
R(root);//再右旋
}
}
}else{
insert(root->rc,v);
root->height=max(getheight(root->lc),getheight(root->rc))+1;
if(getbalancenum(root)==-2){
if(getbalancenum(root->rc)==-1){//RR型
L(root);//左旋
}else if(getbalancenum(root->rc)==1){//RL型
R(root->rc);//先右旋
L(root);//再左旋
}
}
}
}
int main(){
int n,v;
cin>>n;
while(n--){
cin>>v;
insert(root,v);
}
printf("%d\n",root->v);
return 0;
}