AVL ํธ๋ฆฌ๋ Balanced Binary Search Tree์ด๋ค. AVL ํธ๋ฆฌ๋ ๊ฐ๊ฐ ๋
ธ๋๋ง๋ค ์ผ์ชฝ, ์ค๋ฅธ์กฑ ์๋ธํธ๋ฆฌ์ ๋์ด ์ฐจ์ด์ ๋ํ ์ ๋ณด๋ฅผ๊ฐ์ง๊ณ ์๋ธํธ๋ฆฌ์ ๋์ด ์ฐจ์ด๊ฐ 1๋ณด๋ค ํฌ์ง์๋ค๋ ์ฑ์ง์ ๊ฐ์ง๋ค.(์ํคํผ๋์ )
์ฆ, ์์ชฝ ์๋ธํธ๋ฆฌ์ ๋์ด ์ฐจ์ด๊ฐ 1์ดํ์ด๋ค.
๊ท ํ์กํ AVL ํธ๋ฆฌ๋ n๊ฐ์ ์์๊ฐ ์์ ๋ O(logn)์ ์๊ฐ๋ณต์ก๋๋ก ๊ฒ์, ์ฝ์
, ์ญ์ ๋ฅผ ํ ์ ์๋ค.
์๊ฐ ๋ณต์ก๋
Rotation
ํธ๋ฆฌ์ ์ฌ๊ตฌ์ฑ ์์
์ Rotation(ํ์ )์ด๋ผ๊ณ ํ๋ค.
LL
Copy z y
/ \ / \
y T4 Right Rotate (z) x z
/ \ - - - - - - - - -> / \ / \
x T3 T1 T2 T3 T4
/ \
T1 T2
y๋ z์ ์ผ์ชฝ ์์, x๋ y์ ์ผ์ชฝ ์์์ด๋ค. ์ด๋ T1, T2, T3, T4๋ ๊ฐ๊ฐ์ ์๋ธํธ๋ฆฌ์ด๋ค.
z์ ์ค๋ฅธ์กฑ ์์๊ณผ ์ผ์ชฝ ์์์ด ๋ถ๊ท ํํ๋ฏ๋ก right Rotation ํ๋ฒ์ผ๋ก ๊ท ํ์ ์ก์์ค ์ ์๋ค.
Copy if (bal > 1 && key < node->left->key) return right_rotate(node);
LR
Copy z z x
/ \ / \ / \
y T4 Left Rotate (y) x T4 Right Rotate(z) y z
/ \ - - - - - - - - -> / \ - - - - - - - -> / \ / \
T1 x y T3 T1 T2 T3 T4
/ \ / \
T2 T3 T1 T2
y๋ z์ ์ผ์ชฝ ์์, x๋ y์ ์ค๋ฅธ์ชฝ ์์์ด๋ค. ์ด๋ฌํ ๊ฒฝ์ฐ์๋ ํ์ ์ ๋๋ฒ์์ผ์ค์ผํ๋ค. ์ฐ์ y๋ฅผ ์ผ์ชฝ ํ์ ์ ํ๋ฒ ์์ผ์ฃผ๊ณ z๋ฅผ ์ค๋ฅธ์ชฝ ํ์ ์์ผ์ฃผ๋ฉด ๊ท ํ์ด ์กํ๊ฒ ๋๋ค.
Copy if (bal > 1 && key > node->left->key){
node->left = left_rotate(node->left);
return right_rotate(node);
}
RR
Copy z y
/ \ / \
T1 y Left Rotate(z) z x
/ \ - - - - - - - -> / \ / \
T2 x T1 T2 T3 T4
/ \
T3 T4
y๋ z์ ์ค๋ฅธ์ชฝ ์์์ด๊ณ , x๋ y์ ์ค๋ฅธ์ชฝ ์์์ด๋ค. ์ด๋ฌํ ๊ฒฝ์ฐ๋ LL๊ณผ ๋ง์ฐฌ๊ฐ์ง๋ก ํ๋ฒ์ rotation์ผ๋ก ๊ท ํ์ ์ก์ ์ ์๋ค.
Copy if (bal < -1 && key > node->right->key) return left_rotate(node);
RL
Copy z z x
/ \ / \ / \
T1 y Right Rotate (y) T1 x Left Rotate(z) z y
/ \ - - - - - - - - -> / \ - - - - - - - -> / \ / \
x T4 T2 y T1 T2 T3 T4
/ \ / \
T2 T3 T3 T4
y๋ z์ ์ค๋ฅธ์ชฝ์์, x๋ y์ ์ผ์ชฝ ์์์ด๋ค .์ด๋ฌํ ๊ฒฝ์ฐ๋ ์์ LR๊ณผ ์ ๋ฐ๋์ธ ๊ฒฝ์ฐ์ด๋ค. ์ด ๋๋ ์ค๋ฅธ์ชฝ ํ์ ํ ์ผ์ชฝ ํ์ ์ ํ๋ฉด ๊ท ํ์ ๋ง์ถ ์ ์๋ค.
Copy if (bal < -1 && key < node->right->key){
node->right = right_rotate(node->right);
return left_rotate(node);
}
๊ตฌํ
Copy typedef struct node{
int key;
struct node * left, *right;
int height; // ๋์ด
}Node;
Node * new_node(int key){
Node * new = (Node *)malloc(sizeof(Node));
new->key = key;
new->height = 0; //์๋ก์ด ๋
ธ๋๋ ๊ธฐ๋ณธ์ ์ผ๋ก ๋จ๋ง ๋
ธ๋์ height๋ฅผ ๊ฐ์ง๋ค.
new->left = new->right = NULL;
return new;
}
height
Copy int height(Node * node){
if(node == NULL) return -1;
return node->height;
}
Right Rotation
Copy /*
z y(l)
/ \ / \
y T4 Right Rotate (z) x z(node)
/ \ - - - - - - - - -> / \ / \
x T3 T1 T2 T3(r) T4
/ \
T1 T2
*/
Node * right_rotate(Node * node){
Node * l = node->left;
Node * r = l->right;
l->right = node;
node->left = r;
node->height = 1+MAX(height(node->left),height(node->right));
l->height = 1+MAX(height(l->left),height(l->right));
return l;
}
Left Rotation
Copy /*
z y(r)
/ \ / \
T1 y Left Rotate(z) z(node) x
/ \ - - - - - - - -> / \ / \
T2 x T1 T2(l) T3 T4
/ \
T3 T4
*/
Node * left_rotate(Node * node){
Node * r = node->right;
Node * l = r->left;
r->left = node;
node->right =l;
node->height = 1+MAX(height(node->left),height(node->right));
r->height = 1+MAX(height(r->left),height(r->right));
return r;
}
balance
Copy int balance(Node * node){
if(node == NULL) return 0;
// ์์ชฝ ์๋ธํธ๋ฆฌ์ ๋์ด๋ฅผ ๋น๊ตํ๋ค.
return height(node->left)-height(node->right);
}
์ฝ์
์์ Rotation์ ์ด์ฉํด์ ์ฝ์
์ ๊ตฌํํ ์ ์๋ค.
์ฐ์ BST์ ์ฝ์
๊ณผ ๊ฐ์ด ์ฝ์
ํ๋ค.
ํ์ฌ์ height๊ฐ์ updateํด์ค๋ค.
balanceํ์ง ํ์ธํ๋ค.(-1๋ฏธ๋ง 1์ด๊ณผ ๋ถ๊ท ํ)
๋ถ๊ท ํํ๋ค๋ฉด LL, LR, RR, RL ์ ๊ฐ๊ฐ์ ๊ฒฝ์ฐ์ ๋ง๊ฒ rotationํด์ค๋ค.
Copy Node * insert(Node * node, int key){
// 1. ๋จผ์ Binary Search Tree์ ์ฝ์
๊ณผ ๊ฐ์ด ์ฝ์
ํ๋ค.
if (node == NULL)
return(new_node(key));
if (key < node->key)node->left = insert(node->left, key);
else if (key > node->key) node->right = insert(node->right, key);
else return node; //๊ฐ์ด ๊ฐ์ ๊ฒฝ์ฐ์๋ BST์ ์ฝ์
๊ณผ ๊ฐ์ง ์๊ณ ๋ฐ๋ก ๋ฆฌํดํด์ค๋ค.
// 2. height๊ฐ์ ๋ณ๊ฒฝํด์ค๋ค.
node->height = 1 + MAX(height(node->left),height(node->right));
// 3. balanceํ์ง ํ์ธ์ ํ๋ค.(-1๋ฏธ๋ง 1์ด๊ณผ๋ฉด ๋ถ๊ท ํ)
int bal = balance(node);
// 4. ๋ถ๊ท ํํ ๊ฒฝ์ฐ์ rotation!
// LL
if (bal > 1 && key < node->left->key) return right_rotate(node);
// RR
if (bal < -1 && key > node->right->key) return left_rotate(node);
// LR ๋๋ฒํ์ (left->right)
if (bal > 1 && key > node->left->key){
node->left = left_rotate(node->left);
return right_rotate(node);
}
// RL
if (bal < -1 && key < node->right->key){
node->right = right_rotate(node->right);
return left_rotate(node);
}
return node;
}
์ญ์
์ฐ์ BST์ ์ญ์ ์ ๊ฐ์ด ์ญ์ ํ๋ค.
ํ์ฌ ๋
ธ๋๋ ๋ฐ๋์ ์ญ์ ๋
ธ๋์ ์กฐ์๋
ธ๋ ์ค ํ๋์ฌ์ผํ๋ค.
ํ์ฌ์ height๊ฐ์ updateํด์ค๋ค.
balanceํ์ง ํ์ธํ๋ค.(-1๋ฏธ๋ง 1์ด๊ณผ ๋ถ๊ท ํ)
๋ถ๊ท ํํ๋ค๋ฉด LL, LR, RR, RL ์ ๊ฐ๊ฐ์ ๊ฒฝ์ฐ์ ๋ง๊ฒ rotationํด์ค๋ค.
Copy Node* delete(Node* root, int key){
Node * tmp;
// 1. BST ์ญ์
if (root == NULL) return root;
if ( key < root->key )root->left = delete(root->left, key);
else if( key > root->key ) root->right = delete(root->right, key);
else{// ํค๊ฐ์ด ๊ฐ์ผ๋ฉด ๊ทธ ๋
ธ๋๋ฅผ ์ญ์
if(root->left == NULL || root->right == NULL){
if(root->left!=NULL)tmp = root->left;
else tmp =root->right;
// ์์์ด ์๋ ๊ฒฝ์ฐ
if (tmp == NULL){
tmp = root;
root = NULL;
}
else *root = *tmp; // ์์์ด ํ๊ฐ์ธ ๊ฒฝ์ฐ
free(tmp);
}else{//์์์ด ๋๊ฐ์ธ ๊ฒฝ์ฐ
tmp = min(root->right);
root->key = tmp->key;
root->right = delete(root->right, tmp->key);
}
}
// ์ญ์ ํ์ root๊ฐ NULL์ธ๊ฒฝ์ฐ
if (root == NULL) return root;
// ํ์ฌ height๋ฅผ updateํด์ค๋ค.
root->height = 1 + MAX(height(root->left),height(root->right));
// balance ๊ฐ์ ๊ฐ์ ธ์จ๋ค.
int bal = balance(root);
// ๋ถ๊ท์นํ ๊ฒฝ์ฐ
// LL
if (bal > 1 && balance(root->left) >= 0)
return right_rotate(root);
// LR
if (bal > 1 && balance(root->left) < 0){
root->left = left_rotate(root->left);
return right_rotate(root);
}
// RR
if (bal < -1 && balance(root->right) <= 0)
return left_rotate(root);
// RL
if (bal < -1 && balance(root->right) > 0){
root->right = right_rotate(root->right);
return left_rotate(root);
}
return root;
}