#include "BinarySearchTree.h" #include using namespace std; template class AVLTree : public BinarySearchTree { protected: /** function to set the height correctly **/ void _setHeight(typename BinaryTree::Iterator position) { int leftheight = -1; int rightheight = -1; //get left child's height if (position.hasLeftChild()) leftheight = BinaryTree::getAuxiliary(position.left()); //get right child's height if (position.hasRightChild()) rightheight = BinaryTree::getAuxiliary(position.right()); //set position's height if (leftheight > rightheight) BinaryTree::setAuxiliary(leftheight+1, position); else BinaryTree::setAuxiliary(rightheight+1, position); } bool _isBalanced(typename BinaryTree::Iterator position) { int leftheight = -1; int rightheight = -1; //get left child's height if (position.hasLeftChild()) leftheight = BinaryTree::getAuxiliary(position.left()); //get right child's height if (position.hasRightChild()) rightheight = BinaryTree::getAuxiliary(position.right()); int balancefactor = abs(leftheight-rightheight); return (balancefactor <= 1); } typename BinaryTree::Iterator _getHigherChild(typename BinaryTree::Iterator position) { if (position.hasLeftChild() && !position.hasRightChild()) return position.left(); else if (position.hasRightChild() && !position.hasLeftChild()) return position.right(); else { //know there is both a left and right child if (BinaryTree::getAuxiliary(position.right()) > BinaryTree::getAuxiliary(position.left())) return position.right(); else return position.left(); } } public: void insert(const ItemType& value) { //insert the value into the tree BinarySearchTree::insert(value); typename BinaryTree::Iterator current, parent, grandparent, x,y,z; //set correct height of new node current = BinarySearchTree::find(value); _setHeight(current); //check and fix the rest of the tree if not at the root if (!current.isRoot()) { //check parent's height parent = current.up(); _setHeight(parent); while (!parent.isRoot()) { grandparent = parent.up(); _setHeight(grandparent); //check to see if we need a rotation if (!_isBalanced(grandparent)) { z = grandparent; y = _getHigherChild(z); x = _getHigherChild(y); if ((y == z.left() && x == y.left()) || (y == z.right() && x == y.right())) { pivot(y); _setHeight(z); _setHeight(y); grandparent = y; } else { pivot(x); pivot(x); _setHeight(y); _setHeight(z); _setHeight(x); grandparent = x; } } //end of !isBalanced //update parent and continue the loop parent = grandparent; } //end of while } //end of if } //end insert }; //end AVLTree class