= =AVL树和伸展树的代码实现
//ConstVar.h常数定义
#ifndef MYOOP_CONSTVAR_H
#define MYOOP_CONSTVAR_H
const int PREORDER = 1;
const int INORDER = 2;
const int POSTORDER = 3;
#endif //MYOOP_CONSTVAR_H
//AVL树
#ifndef MYOOP_AVLTREE_H
#define MYOOP_AVLTREE_H
#include <iostream>
#include "ConstVar.h"
#include <algorithm>
using std::max;
template <class T>
class AVLNode{
public:
T element;
int height;
AVLNode* parent;
AVLNode* left;
AVLNode* right;
AVLNode(const T& element,AVLNode* parent ){
height = 0;
this->element = element;
this->parent = parent;
left = right = nullptr;
}
};
template <class T>
class AVLTree{
private:
AVLNode<T> * root;
public:
AVLTree();
~AVLTree();
AVLTree(const AVLTree & tree);
AVLNode<T>* getRoot();
AVLNode<T>* find(const T& value);
void insert(const T& value);
void remove(const T& value);
void printTree(const int & code);
void makeEmpty();
private:
int Height(const AVLNode<T>* tree) const ;
void leftRotation(AVLNode<T>* aboveNode);
void rightRotation(AVLNode<T>* aboveNode);
AVLNode<T> *findMin(AVLNode<T>* tree) const ;
void insert(const T& value, AVLNode<T>* parent);
void remove(const T &value,AVLNode<T>* &tree);
void replace(AVLNode<T>* ori,AVLNode<T>* to);
void inorder(const AVLNode<T>* tree) const ;
void preorder(const AVLNode<T>* tree) const ;
void postorder(const AVLNode<T>* tree) const ;
void makeEmpty(AVLNode<T>* &tree);
};
template <class T>
AVLTree<T>::AVLTree() {
root = nullptr;
}
template <class T>
AVLTree<T>::~AVLTree() {
makeEmpty();
}
template <class T>
AVLTree<T>::AVLTree(const AVLTree<T> &tree) {
this->root = tree.root;
}
template <class T>
AVLNode<T>* AVLTree<T>::getRoot() {
return root;
}
template <class T>
AVLNode<T>* AVLTree<T>::find(const T &value) {
if(!this->root) return nullptr;
AVLNode<T>* cur = this->root;
while(cur != nullptr){
if(cur->element == value) return cur;
else if(value<cur->element){
cur = cur->left;
}else{
cur = cur->right;
}
}
return nullptr;
}
template <class T>
int AVLTree<T>::Height(const AVLNode<T>* tree)const {
if(!tree) return -1;
else return tree->height;
}
template <class T>
void AVLTree<T>::leftRotation(AVLNode<T> *aboveNode) {
AVLNode<T>* child = aboveNode->right;
if(child){
aboveNode->right = child->left;
if(child->left) child->left->parent = aboveNode;
child->parent = aboveNode->parent;
child->left = aboveNode;
}
if(!aboveNode->parent){
root = child;
}else if(aboveNode==aboveNode->parent->left)
aboveNode->parent->left = child;
else
aboveNode->parent->right = child;
aboveNode->parent = child;
aboveNode->height = max(Height(aboveNode->left),Height(aboveNode->right))+1;
if(child) child->height = max(Height(child->left),Height(child->right))+1;
}
template <class T>
void AVLTree<T>::rightRotation(AVLNode<T> *aboveNode) {
AVLNode<T>* child = aboveNode->left;
if(child){
aboveNode->left = child->right;
if(child->right) child->right->parent = aboveNode;
child->parent = aboveNode->parent;
child->right = aboveNode;
}
if(!aboveNode->parent){
root = child;
}else if(aboveNode==aboveNode->parent->left)
aboveNode->parent->left = child;
else
aboveNode->parent->right = child;
aboveNode->parent = child;
aboveNode->height = max(Height(aboveNode->left),Height(aboveNode->right))+1;
if(child) child->height = max(Height(child->left),Height(child->right))+1;
}
template <class T>
void AVLTree<T>::printTree(const int &code) {
switch(code){
case PREORDER:
preorder(this->root);
break;
case INORDER:
inorder(this->root);
break;
case POSTORDER:
postorder(this->root);
break;
default:break;
}
std::cout<<std::endl;
}
template <class T>
void AVLTree<T>::preorder(const AVLNode<T> *tree) const {
if(tree){
std::cout<<tree->element<<' ';
preorder(tree->left);
preorder(tree->right);
}
}
template <class T>
void AVLTree<T>::inorder(const AVLNode<T> *tree) const {
if(tree){
inorder(tree->left);
std::cout<<tree->element<<' ';
inorder(tree->right);
}
}
template <class T>
void AVLTree<T>::postorder(const AVLNode<T> *tree) const {
if(tree){
postorder(tree->left);
postorder(tree->right);
std::cout<<tree->element<<' ';
}
}
template <class T>
void AVLTree<T>::makeEmpty() {
makeEmpty(root);
}
template <class T>
void AVLTree<T>::makeEmpty(AVLNode<T> *&tree) {
if(!tree) return ;
if(tree->left) makeEmpty(tree->left);
if(tree->right) makeEmpty(tree->right);
delete tree;
tree = nullptr;
}
template <class T>
AVLNode<T>* AVLTree<T>::findMin(AVLNode<T> *tree) const {
if(!tree) return nullptr;
while(tree->left != nullptr) tree = tree->left;
return tree;
}
template <class T>
void AVLTree<T>::insert(const T &value) {
if(!root) root = new AVLNode<T>(value, nullptr);
else insert(value,root);
}
template <class T>
void AVLTree<T>::insert(const T &value, AVLNode<T> *parent) {
if(value < parent->element){
if(parent->left){
insert(value,parent->left);
}else{
parent->left = new AVLNode<T>(value,parent);
}
parent->height = max(Height(parent->left),Height(parent->right))+1;
if(Height(parent->left)-Height(parent->right)==2){
if(value<parent->left->element){
//ll
rightRotation(parent);
}else{
//lr
leftRotation(parent->left);
rightRotation(parent);
}
}
}else if(value > parent->element){
if(parent->right){
insert(value,parent->right);
}else{
parent->right = new AVLNode<T>(value,parent);
}
parent->height = max(Height(parent->left),Height(parent->right))+1;
if(Height(parent->right)-Height(parent->left)==2){
if(value>parent->right->element){
//rr
leftRotation(parent);
}else{
//rl
rightRotation(parent->right);
leftRotation(parent);
}
}
}else{
//do nothing
}
}
template <class T>
void AVLTree<T>::replace(AVLNode<T> *ori, AVLNode<T> *to) {
if(ori->parent==nullptr)
this->root = to;
else if(ori == ori->parent->left)
ori->parent->left = to;
else
ori->parent->right = to;
if(to != nullptr) to->parent = ori->parent;
}
template <class T>
void AVLTree<T>::remove(const T &value) {
remove(value,root);
}
template <class T>
void AVLTree<T>::remove(const T &value,AVLNode<T> *&tree) {
if(!tree) return ;
if(value<tree->element){
remove(value,tree->left);
if(Height(tree->right)-Height(tree->left)==2){
if(Height(tree->right->right)>=Height(tree->right->left)){
leftRotation(tree);
}else{
rightRotation(tree->right);
leftRotation(tree);
}
}
}else if(value>tree->element){
remove(value,tree->right);
if(Height(tree->left)-Height(tree->right)==2){
if(Height(tree->left->left)>=Height(tree->left->right)){
rightRotation(tree);
}else{
leftRotation(tree->left);
rightRotation(tree);
}
}
}else{
if(tree->left!=nullptr && tree->right!= nullptr){
AVLNode<T>* minnode = findMin(tree->right);
tree->element = minnode->element;
minnode->element = value;
remove(value,tree->right);
tree->height = max(Height(tree->left),Height(tree->right))+1;
}else if(tree->left == nullptr){
replace(tree,tree->right);
}else if(tree->right == nullptr){
replace(tree,tree->left);
}
}
if(tree) tree->height = max(Height(tree->left),Height(tree->right))+1;
}
#endif //MYOOP_AVLTREE_H
//伸展树
#ifndef MYOOP_SPLAYTREE_H
#define MYOOP_SPLAYTREE_H
#include <iostream>
#include "ConstVar.h"
#include "AVLTree.h"
template <class T>
class SPTNode{
public:
T element;
SPTNode* parent;
SPTNode* left;
SPTNode* right;
SPTNode(const T& element,SPTNode* parent ){
this->element = element;
this->parent = parent;
left = right = nullptr;
}
};
template <class T>
class SPTree{
private:
SPTNode<T> * root;
public:
SPTree();
~SPTree();
SPTree(const SPTree & tree);
SPTNode<T>* getRoot();
SPTNode<T>* find(const T& value);
void insert(const T& value);
void remove(const T& value);
void printTree(const int & code);
void makeEmpty();
private:
void leftRotation(SPTNode<T>* aboveNode);
void rightRotation(SPTNode<T>* aboveNode);
void splay(SPTNode<T>* node);
SPTNode<T> *findMin(SPTNode<T>* tree) const ;
void insert(const T& value, SPTNode<T>* parent);
void remove(SPTNode<T>* &target);
void replace(SPTNode<T>* ori,SPTNode<T>* to);
void inorder(const SPTNode<T>* tree) const ;
void preorder(const SPTNode<T>* tree) const ;
void postorder(const SPTNode<T>* tree) const ;
void makeEmpty(SPTNode<T>* &tree);
};
template <class T>
SPTree<T>::SPTree() {
root = nullptr;
}
template <class T>
SPTree<T>::~SPTree() {
makeEmpty();
}
template <class T>
SPTree<T>::SPTree(const SPTree & tree) {
this->root = tree.root;
}
template <class T>
SPTNode<T>* SPTree<T>::getRoot() {
return this->root;
}
template <class T>
void SPTree<T>::leftRotation(SPTNode<T> *aboveNode) {
SPTNode<T>* child = aboveNode->right;
if(child){
aboveNode->right = child->left;
if(child->left) child->left->parent = aboveNode;
child->parent = aboveNode->parent;
child->left = aboveNode;
}
if(!aboveNode->parent){
root = child;
}else if(aboveNode==aboveNode->parent->left)
aboveNode->parent->left = child;
else
aboveNode->parent->right = child;
aboveNode->parent = child;
}
template <class T>
void SPTree<T>::rightRotation(SPTNode<T> *aboveNode) {
SPTNode<T>* child = aboveNode->left;
if(child){
aboveNode->left = child->right;
if(child->right) child->right->parent = aboveNode;
child->parent = aboveNode->parent;
child->right = aboveNode;
}
if(!aboveNode->parent){
root = child;
}else if(aboveNode==aboveNode->parent->left)
aboveNode->parent->left = child;
else
aboveNode->parent->right = child;
aboveNode->parent = child;
}
template <class T>
void SPTree<T>::splay(SPTNode<T> *node) {
if(!node) return ;
while(node->parent){
if(!node->parent->parent){
if(node==node->parent->left){
rightRotation(node->parent);
}else{
leftRotation(node->parent);
}
}else{
if(node==node->parent->left&&node->parent==node->parent->parent->left){
rightRotation(node->parent->parent);
rightRotation(node->parent);
}else if(node==node->parent->right && node->parent==node->parent->parent->right){
leftRotation(node->parent->parent);
leftRotation(node->parent);
}else if(node==node->parent->right && node->parent==node->parent->parent->left){
leftRotation(node->parent);
rightRotation(node->parent);
}else{
rightRotation(node->parent);
leftRotation(node->parent);
}
}
}
}
template <class T>
SPTNode<T>* SPTree<T>::find(const T &value) {
if(!root) return nullptr;
SPTNode<T>* cur = root;
while(cur!=nullptr){
if(value<cur->element){
cur = cur->left;
}else if(value>cur->element){
cur = cur->right;
}else{
break;
}
}
if(cur) splay(cur);
return root;
}
template <class T>
SPTNode<T>* SPTree<T>::findMin(SPTNode<T> *tree) const {
if(!tree) return nullptr;
while(tree->left) tree = tree->left;
return tree;
}
template <class T>
void SPTree<T>::insert(const T &value) {
if(!this->root){
this->root = new SPTNode<T>(value, nullptr);
}else{
insert(value,this->root);
}
}
template <class T>
void SPTree<T>::insert(const T &value, SPTNode<T> *parent) {
SPTNode<T>* newOne = nullptr;
if(value<parent->element){
if(parent->left == nullptr){
newOne = parent->left = new SPTNode<T>(value,parent);
}else{
insert(value,parent->left);
}
}else if(value>parent->element){
if(parent->right == nullptr){
newOne = parent->right = new SPTNode<T>(value,parent);
}else{
insert(value,parent->right);
}
}else{
return ;
}
splay(newOne);
}
template <class T>
void SPTree<T>::replace(SPTNode<T> *ori, SPTNode<T> *to) {
if(ori->parent==nullptr)
this->root = to;
else if(ori == ori->parent->left)
ori->parent->left = to;
else
ori->parent->right = to;
if(to != nullptr) to->parent = ori->parent;
}
template <class T>
void SPTree<T>::remove(const T &value) {
if(!this->root) return ;
SPTNode<T>* cur = this->root;
while(cur != nullptr){
if(cur->element == value) break;
else if(value<cur->element){
cur = cur->left;
}else{
cur = cur->right;
}
}
if(cur) {
splay(cur);
remove(cur);
}
}
template <class T>
void SPTree<T>::remove(SPTNode<T> *&target) {
if(!target->left) replace(target,target->right);
else if(!target->right) replace(target,target->left);
else{
SPTNode<T>* child = findMin(target->right);
if(child->parent != target){
replace(child,child->right);
child->right = target->right;
child->right->parent = child;
}
replace(target,child);
child->left = target->left;
child->left->parent = child;
}
delete target;
}
template <class T>
void SPTree<T>::printTree(const int &code) {
switch(code){
case PREORDER:
preorder(this->root);
break;
case INORDER:
inorder(this->root);
break;
case POSTORDER:
postorder(this->root);
break;
default:break;
}
std::cout<<std::endl;
}
template <class T>
void SPTree<T>::inorder(const SPTNode<T> *tree) const {
if(tree){
inorder(tree->left);
std::cout<<tree->element<<' ';
inorder(tree->right);
}
}
template <class T>
void SPTree<T>::preorder(const SPTNode<T> *tree) const {
if(tree){
std::cout<<tree->element<<' ';
preorder(tree->left);
preorder(tree->right);
}
}
template <class T>
void SPTree<T>::postorder(const SPTNode<T> *tree) const {
if(tree){
postorder(tree->left);
postorder(tree->right);
std::cout<<tree->element<<' ';
}
}
template <class T>
void SPTree<T>::makeEmpty() {
makeEmpty(root);
}
template <class T>
void SPTree<T>::makeEmpty(SPTNode<T> *&tree) {
if(!tree) return;
if(tree->left)makeEmpty(tree->left);
if(tree->right)makeEmpty(tree->right);
delete tree;
tree = nullptr;
}
#endif //MYOOP_SPLAYTREE_H
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。