#define EQ(a, b) ((a) == (b)) #define LT(a, b) ((a) < (b)) #define LQ(a, b) ((a) <= (b)) typedef int KeyType; typedef struct...{ KeyType key; }ElemType; //binary tree node typedef struct BNode...{ ElemType data; struct BNode *left; struct BNode *right; }BNode, *BTree;
源文件:
#include "dsearch.h" #include "stdio.h" #include "stdlib.h" /**//** * search the binary search tree * if find it, p point to it, * if not find, p point to the last of the path. * f is the parent of tree. */ bool searchBST(BTree tree, KeyType key, BTree f, BTree &p)...{ if(!tree)...{ p = f; return0; }else...{ if(EQ(tree->data.key, key))...{ p = tree; printf("find %d ", key); return1; }else...{ if(LT(key, tree->data.key))...{ return searchBST(tree->left, key, tree, p); }else...{ return searchBST(tree->right, key, tree, p); } } } } //insert the node bool insertBST(BTree &T, ElemType e)...{ BTree p; if(!searchBST(T, e.key, NULL, p))...{ BTree s = (BTree)malloc(sizeof(BNode)); s->data = e; s->left = s->right = NULL; if(!p)...{ T = s; }else...{ if(LT(e.key, p->data.key))...{ p->left = s; }else...{ p->right = s; } } printf("insert %d ", e.key); return1; }else...{ return0; } } int deleteNode(BTree &p)...{ BTree q, s; if(!p->right)...{ printf("%d's right is null, delete %d ", p->data, p->data); q = p; p = p->left; free(q); }else...{ if(!p->left)...{ printf("%d's left is null, delete %d ", p->data, p->data); q = p; p = p->right; free(q); }else...{ //both the left and right are not null printf("%d's left and right are not null, delete %d ", p->data, p->data); q = p; s = p->left; while(s->right)...{ q = s; s = s->right; } p->data = s->data; if(q != p)...{ q->right = s->left; }else...{ q->left = s->left; } free(s); } } return1; } //delete a node int deleteBST(BTree &T, KeyType key)...{ if(!T)...{ return0; }else...{ if(EQ(key, T->data.key))...{ return deleteNode(T); }else...{ if(LT(key, T->data.key))...{ return deleteBST(T->left, key); }else...{ return deleteBST(T->right, key); } } return1; } } void main()...{ /**//** * when use this stmt: BTree tree; * program will run error, why? * see the first stmt of searchBST. */ BTree tree = NULL; ElemType e; int w[] =...{45, 24, 53, 45, 12, 24, 90}; for(int i =0; i <7; i++)...{ e.key = w[i]; insertBST(tree, e); } deleteBST(tree, 24); deleteBST(tree, 53); deleteBST(tree, 45); }
程序的执行结果:
insert 45 insert 24 insert 53 find 45 insert 12 find 24 insert 90 24's right is null, delete 24 53's left is null, delete 53 45's left and right are not null, delete 45
(2)平衡二叉树
左右子树的深度之差的绝对值不超过1。
结论:
a. 无论哪种情况,在经过平衡旋转处理之后,以*b或者*c为根的新子树为平衡二叉树,而且它的深度和插入之前以*a为根的子树相同。
b. 当平衡的二叉树因为插入新的节点而失去平衡时,只需要调整最小不平衡子树即可。
c.在平衡树上进行查找的时间复杂度为O(log(n))。
头文件:
#define EQ(a, b) ((a) == (b)) #define LT(a, b) ((a) < (b)) #define LQ(a, b) ((a) <= (b)) #define LH 1 #define EH 0 #define RH -1 typedef int KeyType; typedef struct...{ KeyType key; }ElemType; //binary tree node typedef struct BSTNode...{ ElemType data; //the balance factor int bf; struct BSTNode *left; struct BSTNode *right; }BSTNode, *BSTree;
源文件:
#include "avl.h" #include "stdio.h" #include "stdlib.h" void r_rotate(BSTree &p)...{ BSTree lc = p->left; p->left = lc->right; lc->right = p; p = lc; } void l_rotate(BSTree &p)...{ BSTree rc = p->right; p->right = rc->left; rc->left = p; p = rc; } void leftBalance(BSTree &T)...{ BSTree lc = T->left; switch(lc->bf)...{ case LH: printf("right "); T->bf = lc->bf = EH; r_rotate(T); break; case RH: printf("left right "); BSTree rd = lc->right; switch(rd->bf)...{ case LH: T->bf = RH; lc->bf = EH; break; case EH: T->bf = lc->bf = EH; break; case RH: T->bf = EH; lc->bf = LH; break; } rd->bf = EH; l_rotate(T->left); r_rotate(T); break; } } void rightBalance(BSTree &T)...{ BSTree rc = T->right; switch(rc->bf)...{ case RH: printf("left "); T->bf = rc->bf = EH; l_rotate(T); break; case LH: printf("right left "); BSTree ld = rc->left; switch(ld->bf)...{ case RH: T->bf = LH; rc->bf = EH; break; case EH: T->bf = rc->bf = EH; break; case LH: T->bf = EH; rc->bf = RH; break; } ld->bf = EH; r_rotate(T->right); l_rotate(T); break; } } /**//** * if e does not exists in t, insert it and return 1, * ortherwise return 0; * taller: is the tree get higher? */ int insertAVL(BSTree &T, ElemType e, int&taller)...{ if(!T)...{ //insert the new node printf("insert a new node:%d ", e.key); T = (BSTree)malloc(sizeof(BSTNode)); T->data = e; T->left = T->right = NULL; T->bf = EH; taller =1; }else...{ //there is the same key in the tree, need no insert. if(EQ(e.key, T->data.key))...{ printf("the node %d is in the tree ", e.key); taller =0; return0; } //insert in the left of t if(LT(e.key, T->data.key))...{ //not insert if(!insertAVL(T->left, e, taller))...{ return0; } if(taller)...{ switch(T->bf)...{ case LH: //left was higher than right, and //insert in the left, no balance again. leftBalance(T); taller =0; break; case EH: T->bf = LH; taller =1; break; case RH: T->bf = EH; taller =0; break; } } }else...{ //insert in the right of t //not insert. if(!insertAVL(T->right, e, taller))...{ return0; } if(taller)...{ switch(T->bf)...{ case LH: T->bf = EH; taller =0; break; case EH: T->bf = RH; taller =1; break; case RH: rightBalance(T); taller =0; break; } } } } return1; } void main()...{ BSTree tree = NULL; ElemType e; int taller; int w[] =...{4, 2, 1, 3, 5, 8, 4, 6}; for(int i =0; i <8; i++)...{ e.key = w[i]; insertAVL(tree, e, taller); } }
程序执行结果如下:
insert a new node:4 insert a new node:2 insert a new node:1 right insert a new node:3 insert a new node:5 insert a new node:8 left the node 4isin the tree insert a new node:6 right left Press any key to continue