#include "BST.hpp" /* 任一节点v的平衡因子(balance factor)定义为"其左右子树的高度差",即 balFac(v) = height(lc(v)) - height(rc(c)) 本书中空树高度取-1,单节点子树(叶节点)高度取0 所谓AVL树,即平衡因子受限的二叉搜索树----其中各节点平衡因子的绝对值均不超过1 */ template <typename T> class AVL : public BST<T> { public: BinNodePosi(T) insert(const T& e); bool remove(const T& e); //BST::serach()等其余接口可直接沿用 }; #define Balanced(x) (stature( (x).lc) == stature( (x).rc ) ) //理想平衡条件 #define BalFac(x) (stature( (x).lc) - stature( (x).rc ) ) //平衡因子 #define AvlBalanced(x) ( (-2 < BalFac(x) ) && ( BalFac(x) < 2 ) ) //AVL平衡条件 //在左右孩子中取更高者 //在AVL平衡调整前。借此确定重构方案 #define tallerChild(x) (\ stature( (x)->lc ) > stature( (x)->rc ) ? (x)->lc : ( /*左高*/ \ stature( (x)->lc ) < stature( (x)->rc ) ? (x)->rc : ( /*右高*/ \ IsLChild( *(x) ) ? (x)->lc : (x)->rc \ ) \ ) \ ) //将关键码插入AVL树中 template <typename T> BinNodePosi(T) AVL<T>::insert(const T &e) { BinNodePosi(T) &x = this -> search(e); if (x) { return x; //确认目标节点不存在 } BinNodePosi(T) xx = x = new BinNode<T>(e, this->_hot); this->_size++; //此时,x的父亲_hot若增高,则其祖父有可能失衡 for (BinNodePosi(T) g = this->_hot; g; g = g -> parent) { //从x之父出发向上,逐层检查各代祖先g if ( ! AvlBalanced(*g)) { //一旦发现g失衡,则采用"3+4"算法使之复衡,并将子树重新接入原树 FromParentTo(*g, this->_root) = this -> rotateAt( tallerChild(g)); break; //g复衡后,局部子树高度必然复原;其祖先亦必如此,故调整随机结束 }else{ //否则(g依然平衡),只需简单的更新其高度(注意:即使g为失衡,高度亦可能增加d) this -> updateHeight(g); } }//至多只需一次调整,若果真做过调整,则全树高度必然复原 return xx; //返回新节点位置 }//无论e是否存在于原树中,总有AVL::insert(e)->data == e //从AVL树中删除关键码e template <typename T> bool AVL<T>::remove(const T &e) { BinNodePosi(T) & x = this->search(e); if (!x) { return false; } removeAt(x, this->_hot); this->_size--; for (BinNodePosi(T) g = this->_hot; g; g = g-> parent) { //从_hot出发向上,逐层检查各代祖先g,一旦发现g失衡,则采用"3+4"算法使之复衡,并将子树连至原父亲 if (! AvlBalanced(*g)) { g = FromParentTo(*g, this->_root) = this->rotateAt(tallerChild(tallerChild(g))); } this->updateHeight(g); } return true; }
浙公网安备 33010602011771号