이진탐색트리: 이진트리의 한 종류 2022.04.11 - [자료구조] - [자료구조] 이진탐색트리(binary search tree)
이진탐색트리의 조건: smaller to the left, larger to the right
AVL tree: 이진탐색트리의 한 종류 (not perfectly balanced)
시간복잡도: O(log2n)
AVL tree의 조건: -1 <= BF <= 1
BF: 왼쪽 subtree의 height(높이) - 오른쪽 subtree의 height
->왼쪽과 오른쪽 subtree의 균형을 맞추어 주기 위한 목적
->왼쪽과 오른쪽의 height의 차이 즉, BF의 절대값이 클수록 노드 탐색 시간이 길어지기 때문이다
따라서 새로운 노드가 삽입된 후 BF의 절대값이 1보다 크다면 re-balancing 작업을 수행해야 한다.
경우에 따라 re-balancing하는 방법이 조금씩 다르다.
1. LL (right rotation)
Right Rotation 수행후 re-balacing 된 AVL tree의 모습이다.
2. RR (left rotation)
Left Rotation 수행후 re-balacing 된 AVL tree의 모습이다.
3. RL(double rotation: right rotation -> left rotation)
Right Rotation
Left Rotation 수행후 re-balacing 된 AVL tree의 모습이다.
4. LR(double rotation: left rotation -> right rotation)
Left Rotation
Right Rotation 수행후 re-balacing 된 AVL tree의 모습이다.
// source from https://www.thecrazyprogrammer.com/2014/03/c-program-for-avl-tree-implementation.html
#include <stdio.h>
#include <stdlib.h>
typedef struct node
{
int data;
struct node *left,*right;
int ht;
}node;
node *insert(node *,int);
node *Delete(node *,int);
void preorder(node *);
void inorder(node *);
int height( node *);
node *rotateright(node *);
node *rotateleft(node *);
node *RR(node *);
node *LL(node *);
node *LR(node *);
node *RL(node *);
int BF(node *);
int main()
{
node *root=NULL;
int x,n,i,op;
do
{
printf("\n1)Create:");
printf("\n2)Insert:");
printf("\n3)Delete:");
printf("\n4)Print:");
printf("\n5)Quit:");
printf("\n\nEnter Your Choice:");
scanf("%d",&op);
switch(op)
{
case 1: printf("\nEnter no. of elements:");
scanf("%d",&n);
printf("\nEnter tree data:");
root=NULL;
for(i=0;i<n;i++)
{
scanf("%d",&x);
root=insert(root,x);
}
break;
case 2: printf("\nEnter a data:");
scanf("%d",&x);
root=insert(root,x);
break;
case 3: printf("\nEnter a data:");
scanf("%d",&x);
root=Delete(root,x);
break;
case 4: printf("\nPreorder sequence:\n");
preorder(root);
printf("\n\nInorder sequence:\n");
inorder(root);
printf("\n");
break;
}
}while(op!=5);
return 0;
}
node * insert(node *T,int x)
{
if(T==NULL)
{
T=(node*)malloc(sizeof(node));
T->data=x;
T->left=NULL;
T->right=NULL;
}
else
if(x > T->data) // insert in right subtree
{
T->right=insert(T->right,x);
if(BF(T)==-2)
if(x>T->right->data)
T=RR(T);
else
T=RL(T);
}
else
if(x<T->data)
{
T->left=insert(T->left,x);
if(BF(T)==2)
if(x < T->left->data)
T=LL(T);
else
T=LR(T);
}
T->ht=height(T);
return(T);
}
node * Delete(node *T,int x)
{
node *p;
if(T==NULL)
{
return NULL;
}
else
if(x > T->data) // insert in right subtree
{
T->right=Delete(T->right,x);
if(BF(T)==2)
if(BF(T->left)>=0)
T=LL(T);
else
T=LR(T);
}
else
if(x<T->data)
{
T->left=Delete(T->left,x);
if(BF(T)==-2) //Rebalance during windup
if(BF(T->right)<=0)
T=RR(T);
else
T=RL(T);
}
else
{
//data to be deleted is found
if(T->right!=NULL)
{ //delete its inorder succesor
p=T->right;
while(p->left!= NULL)
p=p->left;
T->data=p->data;
T->right=Delete(T->right,p->data);
if(BF(T)==2)//Rebalance during windup
if(BF(T->left)>=0)
T=LL(T);
else
T=LR(T);\
}
else
return(T->left);
}
T->ht=height(T);
return(T);
}
int height(node *T)
{
int lh,rh;
if(T==NULL)
return(0);
if(T->left==NULL)
lh=0;
else
lh=1+T->left->ht;
if(T->right==NULL)
rh=0;
else
rh=1+T->right->ht;
if(lh>rh)
return(lh);
return(rh);
}
node * rotateright(node *x)
{
node *y;
y=x->left;
x->left=y->right;
y->right=x;
x->ht=height(x);
y->ht=height(y);
return(y);
}
node * rotateleft(node *x)
{
node *y;
y=x->right;
x->right=y->left;
y->left=x;
x->ht=height(x);
y->ht=height(y);
return(y);
}
node * RR(node *T)
{
T=rotateleft(T);
return(T);
}
node * LL(node *T)
{
T=rotateright(T);
return(T);
}
node * LR(node *T)
{
T->left=rotateleft(T->left);
T=rotateright(T);
return(T);
}
node * RL(node *T)
{
T->right=rotateright(T->right);
T=rotateleft(T);
return(T);
}
int BF(node *T)
{
int lh,rh;
if(T==NULL)
return(0);
if(T->left==NULL)
lh=0;
else
lh=1+T->left->ht;
if(T->right==NULL)
rh=0;
else
rh=1+T->right->ht;
return(lh-rh);
}
[자료구조] 트리(tree) 용어 정리하기 (0) | 2022.04.11 |
---|---|
[자료구조] 이진트리(binary tree)의 기본 개념 (0) | 2022.04.11 |
[자료구조] 트리 탐색(tree traversal) 방법- inorder traverse, postorder traverse, preorder traverse, level order traversal (0) | 2022.03.18 |
[자료구조] linked list로 큐(queue) 구현하기 (0) | 2022.03.13 |
[자료구조] linked list로 스택(stack) 구현하기 (0) | 2022.03.13 |
댓글 영역