题目:http://pta.patest.cn/pta/test/16/exam/4/question/668
PTA - Data Structures and Algorithms (English) - 5-6
An AVL tree is a self-balancing binary search tree. In an AVL tree, the heights of the two child subtrees of any node differ by at most one; if at any time they differ by more than one, rebalancing is done to restore this property. Figures 1-4 illustrate the rotation rules.
LL:RR:
RL:
LR:
Now given a sequence of insertions, you are supposed to tell the root of the resulting AVL tree.
Input Specification:
Each input file contains one test case. For each case, the first line contains a positive integer N (≤20) which is the total number of keys to be inserted. Then N distinct integer keys are given in the next line. All the numbers in a line are separated by a space.
Output Specification:
For each test case, print the root of the resulting AVL tree in one line.
Sample Input 1:
5
88 70 61 96 120
Sample Output 1:
70
Sample Input 2:
7
88 70 61 96 120 90 65
Sample Output 2:
88
分析:
1. 树的结点结构
typedef struct node
{
int data;
node* left;
node* right;
int height;
}AVLTreeNode,*AVLTree;
2. 函数声明
int GetHeight(AVLTree A) //获取当前树高
int Max(int x,int y) //用于更新树高
//以下操作返回调整后的AVL树
AVLTree SingleL_Rotation(AVLTree A) //左单旋:LL
AVLTree SingleR_Rotation(AVLTree A) //右单旋:RR
AVLTree DoubleLR_Rotation(AVLTree A) //右左双旋:RL
AVLTree DoubleRL_Rotation(AVLTree A) //左右双旋:LR
AVLTree AVL_Insertion(int x,AVLTree T) //将x插入AVL树T中
3. 函数实现 (以左旋为例):
//左单旋:LL
AVLTree SingleL_Rotation(AVLTree A)
{
//!注:A必须有一个左子节点B
//!左单旋后,更新A和B的高度,返回新的根节点
AVLTree B=A->left;
A->left=B->right;
B->right=A;
A->height=Max(GetHeight(A->left),GetHeight(A->right))+1;
B->height=Max(GetHeight(B->left),A->height)+1;
return B;
}
//左右双旋;LR
AVLTree DoubleLR_Rotation(AVLTree A)
{
//!注:A必须有一个左子结点B,且B必须有一个右子节点C
//!做两次单旋,返回新的根节点:C
A->left=SingleR_Rotation(A->left); //!B和C做右单旋,返回C
return SingleL_Rotation(A); //!A和做左单旋,返回C
}
完整代码:
#include <iostream>
using namespace std;
typedef struct node
{
int data;
node* left;
node* right;
int height;
}AVLTreeNode,*AVLTree;
int GetHeight(AVLTree A)
{
if(A==NULL)return -1;
return A->height;
}
int Max(int x,int y)
{
return (x>y)?x:y;
}
//!左单旋:LL
AVLTree SingleL_Rotation(AVLTree A)
{
//!注:A必须有一个左子节点B
//!左单旋后,更新A和B的高度,返回新的根节点
AVLTree B=A->left;
A->left=B->right;
B->right=A;
A->height=Max(GetHeight(A->left),GetHeight(A->right))+1;
B->height=Max(GetHeight(B->left),A->height)+1;
return B;
}
//!右单旋:RR
AVLTree SingleR_Rotation(AVLTree A)
{
AVLTree C=A->right;
A->right=C->left;
C->left=A;
A->height=Max(GetHeight(A->left),GetHeight(A->right))+1;
C->height=Max(A->height,GetHeight(C->right))+1;
return C;
}
//!左右双旋;LR
AVLTree DoubleLR_Rotation(AVLTree A)
{
//!注:A必须有一个左子结点B,且B必须有一个右子节点C
//!做两次单旋,返回新的根节点:C
A->left=SingleR_Rotation(A->left); //!B和C做右单旋,返回C
return SingleL_Rotation(A); //!A和做左单旋,返回C
}
//!右左双旋:RL
AVLTree DoubleRL_Rotation(AVLTree A)
{
A->right=SingleL_Rotation(A->right);
return SingleR_Rotation(A);
}
//!将x插入AVL树T中,并且返回调整后的AVL树
AVLTree AVL_Insertion(int x,AVLTree T)
{
if(!T) //!若插入空树,则新建包含一个节点的树
{
T=new AVLTreeNode;
T->data=x;
T->height=0;
T->left=T->right=NULL;
}
else if(x<T->data) //!插入T的左子树
{
T->left=AVL_Insertion(x,T->left);
if(GetHeight(T->left)-GetHeight(T->right)==2)
{
//!需左旋
if(x<T->left->data)
T=SingleL_Rotation(T); //!左单旋:LL
else
T=DoubleLR_Rotation(T); //!左右双旋:LR
}
}
else if(x>T->data) //!插入T的右子树
{
T->right=AVL_Insertion(x,T->right);
if(GetHeight(T->left)-GetHeight(T->right)==-2)
{
//!需右旋
if(x>T->right->data)
T=SingleR_Rotation(T); //!右单旋:RR
else
T=DoubleRL_Rotation(T); //!右左双旋:RL
}
}
else //! x==T->data, 无需插入
return T;
//!更新树高
T->height=Max(GetHeight(T->left),GetHeight(T->right))+1;
return T;
}
int main()
{
int n,x;
cin >> n;
AVLTree root=NULL;
for(int i=0;i<n;i++)
{
cin >> x;
root=AVL_Insertion(x,root);
}
cout << root->data << endl;
return 0;
}
转载于:https://www.cnblogs.com/claremore/p/4809392.html