# 二叉查找树

229人阅读 评论(0)

-BinarySearchTree.h

#ifndef __BINARY_SEARCH_TREE_H__
#define __BINARY_SEARCH_TREE_H__

#include <iostream>
#include <string>

template <class Object, class Comparator = std::less<Object> >
class BinarySearchTree {

public:
BinarySearchTree();
BinarySearchTree(const BinarySearchTree& rhs);
~BinarySearchTree();

const Object& findMin()const;
const Object& findMax()const;
bool contains(const Object& x)const;
bool isEmpty()const { return NULL == root; }
void printTree()const;

void makeEmpty();
void insert(const Object& x);
void remove(const Object& x);

const BinarySearchTree& operator=(const BinarySearchTree& rhs);

private:
struct BinaryNode {
Object element;
BinaryNode* left;
BinaryNode* right;

BinaryNode(const Object& theElement, BinaryNode* lt, BinaryNode* rt) :
element(theElement), left(lt), right(rt) {}
};

BinaryNode* root;
Comparator isLessThan;

BinaryNode* findMin(BinaryNode* t)const;
BinaryNode* findMax(BinaryNode* t)const;
bool contains(const Object& x, BinaryNode* t)const;
void printTree(BinaryNode* t)const;
void insert(const Object& x, BinaryNode*& t)const;
void remove(const Object& x, BinaryNode*& t)const;
void makeEmpty(BinaryNode*& t);
BinaryNode* clone(BinaryNode* t)const;

};

// constructor
template <class Object, class Comparator>
BinarySearchTree<Object, Comparator>::BinarySearchTree() {
root = NULL;
}

// copy constructor
template <class Object, class Comparator>
BinarySearchTree<Object, Comparator>::BinarySearchTree(const BinarySearchTree& rhs) {
root = rhs.clone(rhs.root);
}

// destructor
template <class Object, class Comparator>
BinarySearchTree<Object, Comparator>::~BinarySearchTree() {
makeEmpty();
}

/**
* Returns true if x is found in the tree
*/
template <class Object, class Comparator>
bool BinarySearchTree<Object, Comparator>::contains(const Object& x)const {
return contains(x, root);
}

/**
* Internal method to test if an item is in a subtree
* x is item to search for
* t is the node that roots the subtree
*/
template <class Object, class Comparator>
bool BinarySearchTree<Object, Comparator>::contains(const Object& x, BinaryNode* t)const {

if (t == NULL)
return false;
else if (isLessThan(x, t->element))
return contains(x, t->left);
else if (isLessThan(t->element, x))
return contains(x, t->right);
else
return true;	// Match
}

/**
* Insert x into the tree; duplicates are ignored
*/
template <class Object, class Comparator>
void BinarySearchTree<Object, Comparator>::insert(const Object& x) {
insert(x, root);
}

/**
* Internal method to insert into a subtree
* x is the item to insert
* t is the node that roots the subtree
* Set the new root of the subtree
*/
template <class Object, class Comparator>
void BinarySearchTree<Object, Comparator>::insert(const Object& x, BinaryNode*& t)const {
//root = new BinaryNode(2, NULL, NULL);
if (t == NULL)
t = new BinaryNode(x, NULL, NULL);
else if (isLessThan(x, t->element))
insert(x, t->left);
else if (isLessThan(t->element, x))
insert(x, t->right);
else
return;
}

/**
* Return the smallest item
*/
template <class Object, class Comparator>
const Object& BinarySearchTree<Object, Comparator>::findMin()const {

BinaryNode* node = findMin(root);

if (NULL == node) throw out_of_range("BinarySearchTree is empty.");

else return node->element;

}

/**
* Internal method to find the smallest item in a subtree t.
* Return node containing the smallest item
*/
template <class Object, class Comparator>
typename BinarySearchTree<Object, Comparator>::BinaryNode*
BinarySearchTree<Object, Comparator>::findMin(BinaryNode* t)const {

if (t == NULL)
return NULL;
else if (t->left == NULL)
return t;
return findMin(t->left);
}

/**
* Return the largest item
*/
template <class Object, class Comparator>
const Object& BinarySearchTree<Object, Comparator>::findMax()const {

BinaryNode* node = findMax(root);

if (NULL == node) throw out_of_range("BinarySearchTree is empty.");

else return node->element;
}

/**
* Internal method to find the largest item in a subtree t.
* Return node containing the largest item
*/
template <class Object, class Comparator>
typename BinarySearchTree<Object, Comparator>::BinaryNode*
BinarySearchTree<Object, Comparator>::findMax(BinaryNode* t)const {

if (t == NULL)
return NULL;
else if (t->right == NULL)
return t;
return findMax(t->right);
}

/**
* Remove x from the tree
*/
template <class Object, class Comparator>
void BinarySearchTree<Object, Comparator>::remove(const Object& x) {
remove(x, root);
}

/**
* Internal method to remove from a subtree
* x is the item to remove
* t is the node that roots the subtree
* Set the new root of the subtree
*/
template <class Object, class Comparator>
void BinarySearchTree<Object, Comparator>::remove(const Object& x, BinaryNode*& t)const {

if (NULL == t)
return;
else if (isLessThan(x, t->element))
remove(x, t->left);
else if (isLessThan(t->element, x))
remove(x, t->right);
else if (NULL != t->left && NULL != t->right) {		// there are both left son and right son
// 用结点t的右子树的最小结点来替代t
// 再递归调用从t的右子数中删除t->element这个结点
t->element = findMin(t->right)->element;
remove(t->element, t->right);
}
else {
BinaryNode* oldNode = t;
t = (t->left != NULL) ? t->left : t->right;
delete oldNode;
}
}

// makeEmpty
template <class Object, class Comparator>
void BinarySearchTree<Object, Comparator>::makeEmpty() {
makeEmpty(root);
}

/**
* Internal method to make subtree empty
*/
template <class Object, class Comparator>
void BinarySearchTree<Object, Comparator>::makeEmpty(BinaryNode*& t) {

if (t != NULL) {
makeEmpty(t->left);
makeEmpty(t->right);
delete t;
}
t = NULL;
}

/**
* Deep Copy
*/
template <class Object, class Comparator>
const BinarySearchTree<Object, Comparator>&
BinarySearchTree<Object, Comparator>::operator=(const BinarySearchTree<Object, Comparator>& rhs) {

if (this != &rhs) {
this->makeEmpty();
this->root = rhs.clone(rhs.root);
}
return *this;
}

/**
* Internal method to clone subtree
*/
template <class Object, class Comparator>
typename BinarySearchTree<Object, Comparator>::BinaryNode*
BinarySearchTree<Object, Comparator>::clone(BinaryNode* t)const {

if (t == NULL) return NULL;

else return new BinaryNode(t->element, clone(t->left), clone(t->right));

}

/**
* Print the subtree
*/
template <class Object, class Comparator>
void BinarySearchTree<Object, Comparator>::printTree()const {
printTree(root);
}

/**
* Internal method to print the subtree
*/
template <class Object, class Comparator>
void BinarySearchTree<Object, Comparator>::printTree(BinaryNode* t)const {

if (t == NULL) return;
printTree(t->left);
printTree(t->right);
std::cout << t->element << " ";

}

#endif

-main.cpp

#include "BinarySearchTree.h"
using namespace std;

void printTree(BinarySearchTree<int>& ibst, string s);

int main()
{

BinarySearchTree<int> ibst;

ibst.insert(6);
ibst.insert(2);
ibst.insert(1);
ibst.insert(8);
ibst.insert(7);
ibst.insert(100);

BinarySearchTree<int> ibst2(ibst);
printTree(ibst2, "ibst2");

ibst.remove(7);
ibst.remove(100);

BinarySearchTree<int> ibst3 = ibst;
printTree(ibst3, "ibst3");

ibst.insert(4);
ibst.insert(3);
printTree(ibst, "ibst");

if (ibst.contains(6)) cout << "ibst contains 6" << endl;
else cout << "ibst doesn't contain 6" << endl;
if (ibst.contains(10)) cout << "ibst contains 10" << endl;
else cout << "ibst doesn't contain 10" << endl;

if (!ibst.isEmpty()) cout << "ibst isn't empty" << endl;
else cout << "ibst is empty" << endl;
ibst.makeEmpty();
if (!ibst.isEmpty()) cout << "ibst isn't empty" << endl;
else cout << "ibst is empty" << endl;

system("pause");
return 0;
}

void printTree(BinarySearchTree<int>& ibst, string s) {
cout << s << ": ";
ibst.printTree();
cout << endl;
cout << s << ".max: " << ibst.findMax()
<< "  " << s << ".min: " << ibst.findMin();
cout << endl << endl;
}

0
0

个人资料
• 访问：72546次
• 积分：2234
• 等级：
• 排名：第19852名
• 原创：139篇
• 转载：124篇
• 译文：0篇
• 评论：9条
阅读排行
最新评论