64.0 概述
什么是二叉查找树(binary search tree)?
二叉查找树(binary search tree)又叫二叉排序树(binary ordered tree)。
对于任意二叉查找树,要么是一棵空树,要么具有如下性质:
若它的左子树不为空,则左子树上所有结点的值都小于它的根结点的值;
若它的右子树不为空,则右子树上所有结点的值都大于它的根结点的值;
它的左、右子树也分别为二叉查找树;
中序遍历二叉查找树可得到一个关键字的有序序列,一个无序序列可以通过构造一棵二叉查找树变成一个有序序列,构造树的过程即为对无序序列进行排序的过程;
我们这里用到的二叉查找树的数据部分的数据类型为整型,如下代码为int定义一个别名“ItemType”:
typedef int ItemType;
如下代码是定义二叉查找树结点。每一个结点包含:数据部分,左孩子指针,右孩子指针。
struct TreeNode
{
ItemType info;
TreeNode* left;
TreeNode* right;
};
如下定义二叉查找树类:定义伊始,是一棵空树。
class TreeType {// binary search tree.
public:
TreeType() {
root = NULL;
}
//在这个位置添加二叉查找树的各种操作方法的声明;
TreeNode *root;
};
新建二叉查找树对象:
TreeType binarySearchTree;
64.1 建立二叉查找树
下面,我们在已经定义的空的二叉查找树的基础上,建立有数据的树。
我们的做法是:将如下数组中的15个数据,依次建立二叉查找树。(相当于将数组中数据依次插入之前新建的空的二叉查找树)
ItemType infoArray[15] = {20, 12, 2, 14, 15, 35, 6, 45, 25, 23, 1, 24, 16, 57, 28};
根据二叉查找树的定义和性质,如上数组中的15个数据对应的二叉查找树如下:
算法:
1,第一个被插入的数据(20)成为二叉查找树的根结点;
2,有了根结点之后,后面的数据被插入的位置取决于其与根结点值的大小关系:比根结点的值小,则在根结点的左子树中;比根结点的值大,则在根结点的右子树中。所以,关键是找到被插入数据未来的父结点。这样的父结点需要满足两个条件:其一,其值满足如上的大小关系;其二,其对应的左孩子结点或者右孩子结点(左、右由值的大小关系决定)的位置是空的。
对应C++代码如下:
----------------------------------------------TreeType.h------------------------------------------
TreeType.h
void CreateTree(ItemType *itemArray, int itemNum);
----------------------------------------------TreeType.cpp------------------------------------------
TreeType.cpp
void TreeType::CreateTree(ItemType *itemArray, int itemNum) {
for(int i=0; i<itemNum; i++) {
TreeNode *newnode = new TreeNode;
newnode->info = itemArray[i];
newnode->left = NULL;
newnode->right = NULL;
if(root == NULL) {
root = newnode;
std::cout << itemArray[i] << " will be the root" << endl;
}
else {
TreeNode *parent;
TreeNode *temp = root;
while(temp != NULL) {//这个循环是找未来的父结点。
parent = temp;
if((temp->info) > itemArray[i]) {
temp = temp->left;
}
else {
temp = temp->right;
}
}
if((parent->info) > itemArray[i]) {
//这个if……else……是根据被插入值和父结点的大小关系,确定被插入的位置
parent->left = newnode;
std::cout << itemArray[i] << " will be " << parent->info << "'s left child" << endl;
}
else {
parent->right = newnode;
std::cout << itemArray[i] << " will be " << parent->info << "'s right child" << endl;
}
}
}
}
----------------------------------------------main.cpp------------------------------------------
main.cpp
TreeType binarySearchTree;
ItemType infoArray[15] = {20, 12, 2, 14, 15, 35, 6, 45, 25, 23, 1, 24, 16, 57, 28};
std::cout << "CreateTree: " << endl;
binarySearchTree.CreateTree(infoArray, 15);
std::cout << endl;
输出结果如下:
64.2 遍历二叉查找树
我们在“64.1”中建立了一棵二叉查找树,现在我们想看看这个树中每个结点的内容。我们需要遍历这个二叉查找树。
有三种遍历二叉查找树的方式:(根)前序遍历、(根)中序遍历、(根)后序遍历
如上二叉查找树的(根)前序遍历的结果应该是:20, 12, 2, 1, 6, 14, 15, 16, 35, 25, 23, 24, 28, 45, 57
如上二叉查找树的(根)前序遍历的结果应该是:1, 2, 6, 12, 14, 15, 16, 20, 23, 24, 25, 28, 35, 45, 57
如上二叉查找树的(根)前序遍历的结果应该是:1, 6, 2, 16, 15, 14, 12, 24, 23, 28, 25, 57, 45, 35, 20
我们采用递归的方法来完成遍历。
C++代码如下:
----------------------------------------------TreeType.h------------------------------------------
TreeType.h
void PreorderTraverse(TreeNode *rootNode);//(根)前序遍历
void InorderTraverse(TreeNode *rootNode); //(根)中序遍历
void PostorderTraverse(TreeNode *rootNode); //(根)后序遍历
----------------------------------------------TreeType.cpp------------------------------------------
TreeType.cpp
void TreeType::PreorderTraverse(TreeNode *rootNode) {
if(rootNode!=NULL)
{
std::cout << rootNode->info << " ";//遍历根结点
PreorderTraverse(rootNode->left);//遍历左子树
PreorderTraverse(rootNode->right);//遍历右子树
}
}
void TreeType::InorderTraverse(TreeNode *rootNode) {
if(rootNode!=NULL)
{
InorderTraverse(rootNode->left); //遍历左子树
std::cout << rootNode->info << " ";//遍历根结点
InorderTraverse(rootNode->right); //遍历右子树
}
}
void TreeType::PostorderTraverse(TreeNode *rootNode) {
if(rootNode!=NULL)
{
PostorderTraverse(rootNode->left); //遍历左子树
PostorderTraverse(rootNode->right); //遍历右子树
std::cout << rootNode->info << " ";//遍历根结点
}
}
----------------------------------------------main.cpp------------------------------------------
main.cpp
std::cout << "PreorderTraverse: " << endl;
binarySearchTree.PreorderTraverse(binarySearchTree.root);
std::cout << endl;
std::cout << "InorderTraverse: " << endl;
binarySearchTree.InorderTraverse(binarySearchTree.root);
std::cout << endl;
std::cout << "PostorderTraverse: " << endl;
binarySearchTree.PostorderTraverse(binarySearchTree.root);
std::cout << endl;
std::cout << endl;
输出结果如下:
64.3 向二叉查找树中插入若干个结点
这个方式和“64.1 建立二叉查找树”基本完全相同,此处不赘述,贴出代码如下:
----------------------------------------------TreeType.h------------------------------------------
TreeType.h
void InsertItems(ItemType *itemArray, int itemNum);
----------------------------------------------TreeType.cpp------------------------------------------
TreeType.cpp
void TreeType::InsertItems(ItemType *itemArray, int itemNum) {
for(int i=0; i<itemNum; i++) {
TreeNode *newnode = new TreeNode;
newnode->info = itemArray[i];
newnode->left = NULL;
newnode->right = NULL;
if(root == NULL) {
root = newnode;
std::cout << itemArray[i] << " will be the root" << endl;
}
else {
TreeNode *parent;
TreeNode *temp = root;
while(temp != NULL) {
parent = temp;
if((temp->info) > itemArray[i]) {
temp = temp->left;
}
else if((temp->info) == itemArray[i]) {
break;
}
else {
temp = temp->right;
}
}
if((parent->info) > itemArray[i]) {
parent->left = newnode;
std::cout << itemArray[i] << " will be " << parent->info << "'s left child" << endl;
}
else if((parent->info) == itemArray[i]) {
std::cout << "there has been a " << itemArray[i] << " in the tree" << endl;
}
else {
parent->right = newnode;
std::cout << itemArray[i] << " will be " << parent->info << "'s right child" << endl;
}
}
}
}
----------------------------------------------main.cpp------------------------------------------
main.cpp
/*先插入4个数据,其中的“28”已经在树中,所以实际插入的是3个数据:40、32、42。然后将整棵树按照三种方式分别进行遍历*/
ItemType insertItems[4] = {40, 32, 42, 28};
std::cout << "InsertItems: ";
for (int i=0; i<4; i++) {
std::cout << insertItems[i] << " ";
}
std::cout << endl;
binarySearchTree.InsertItems(insertItems, 4);
std::cout << endl;
std::cout << "PreorderTraverse: " << endl;
binarySearchTree.PreorderTraverse(binarySearchTree.root);
std::cout << endl;
std::cout << "InorderTraverse: " << endl;
binarySearchTree.InorderTraverse(binarySearchTree.root);
std::cout << endl;
std::cout << "PostorderTraverse: " << endl;
binarySearchTree.PostorderTraverse(binarySearchTree.root);
std::cout << endl;
输出结果如下:
对应二叉查找树的示意图如下:
64.4 查找二叉查找树中某个结点
我们采用递归的方法来完成某个结点的查找。
算法:
先查找根结点,若根结点是要找的结点,直接输出根结点内容;
若根结点不是要找的结点,按照递归的方法分别查找左子树和右子树;
C++代码如下:
----------------------------------------------TreeType.h------------------------------------------
TreeType.h
bool FindItem(TreeNode *rootNode, ItemType item);
----------------------------------------------TreeType.cpp------------------------------------------
TreeType.cpp
bool TreeType::FindItem(TreeNode *rootNode, ItemType item) {
if (rootNode == NULL) {
return false;
}
else {
if ((rootNode->info) == item) {
std::cout << "found." << endl;
if ((rootNode->left) != NULL) {
std::cout << "its left child is " << rootNode->left->info << " ." << endl;
}
if ((rootNode->right) != NULL) {
std::cout << "its right child is " << rootNode->right->info << " ." << endl;
}
return true;
}
else {
if (FindItem(rootNode->left, item)) {
return true;
}
if (FindItem(rootNode->right, item)) {
return true;
}
return false;
}
}
}
ItemType TreeType::MinValue(TreeNode *rootNode) {
if(rootNode!=NULL)
{
if ((rootNode->left) != NULL) {
MinValue(rootNode->left);
}
else {
return rootNode->info;
}
}
}
----------------------------------------------main.cpp------------------------------------------
main.cpp
std::cout << endl;
ItemType item = 35;
bool found;
std::cout << "FindItem: " << item << endl;
found = binarySearchTree.FindItem(binarySearchTree.root, item);
std::cout << "found: " << found << endl;
输出结果如下:
64.5 查找二叉查找树中的最大值和最小值
我们知道,二叉查找树是有序序列,而且左子树中所有的值都比根结点的值小,右子树中所有的值都比根结点的值大。所以,最大值是最右边的那个值,最小值是最左边的那个值。进一步分析:最大值为中序遍历的最后一个值,最小值为中序遍历大的第一个值。
C++代码如下:
----------------------------------------------TreeType.h------------------------------------------
TreeType.h
ItemType MinValue(TreeNode *rootNode);
ItemType MaxValue(TreeNode *rootNode);
----------------------------------------------TreeType.cpp------------------------------------------
TreeType.cpp
ItemType TreeType::MaxValue(TreeNode *rootNode) {
if(rootNode!=NULL)
{
if ((rootNode->right) != NULL) {
MaxValue(rootNode->right);
}
else {
return rootNode->info;
}
}
}
----------------------------------------------main.cpp------------------------------------------
main.cpp
std::cout << endl;
std::cout << "MinValue: " << endl;
ItemType minItem = binarySearchTree.MinValue(binarySearchTree.root);
std::cout << "minItem: " << minItem << endl;
std::cout << endl;
std::cout << "MaxValue: " << endl;
ItemType maxItem = binarySearchTree.MaxValue(binarySearchTree.root);
std::cout << "maxItem: " << maxItem << endl;
输出结果如下:
64.6 求二叉查找树的总的结点数
我们采用递归的方法来求二叉查找树的总的结点数。
算法:
总的结点数=左子树的结点数+右子树的结点数+1(根结点)
C++代码如下:
----------------------------------------------TreeType.h------------------------------------------
TreeType.h
int NodesNum(TreeNode *rootNode);
----------------------------------------------TreeType.cpp------------------------------------------
TreeType.cpp
int TreeType::NodesNum(TreeNode *rootNode) {
if(rootNode!=NULL)
{
return (NodesNum(rootNode->left) + NodesNum(rootNode->right) + 1);
}
else {
return 0;
}
}
----------------------------------------------main.cpp------------------------------------------
main.cpp
std::cout << endl;
std::cout << "NodesNum: " << endl;
int num = binarySearchTree.NodesNum(binarySearchTree.root);
std::cout << "NodesNum: " << num << endl;
输出结果如下:
64.7 求二叉查找树中叶子结点的个数及遍历叶子结点
叶子结点,即没有左孩子和右孩子的结点。如上二叉查找树的叶子结点如下图蓝色圈示意:
C++代码实现如下:
----------------------------------------------TreeType.h------------------------------------------
TreeType.h
void LeavesNum(TreeNode *rootNode, int &num);
void PreorderTraverseLeaves(TreeNode *rootNode);
void InorderTraverseLeaves(TreeNode *rootNode);
void PostorderTraverseLeaves(TreeNode *rootNode);
----------------------------------------------TreeType.cpp------------------------------------------
TreeType.cpp
void TreeType::LeavesNum(TreeNode *rootNode, int &num) {
if(rootNode!=NULL)
{
if (((rootNode->left) == NULL) && ((rootNode->right) == NULL)) {
num ++;
}
else {
LeavesNum(rootNode->left, num);
LeavesNum(rootNode->right, num);
}
}
}
void TreeType::PreorderTraverseLeaves(TreeNode *rootNode) {
if(rootNode!=NULL) {
if ((rootNode->left == NULL) && (rootNode->right == NULL)) {
std::cout << rootNode->info << " ";
}
PreorderTraverseLeaves(rootNode->left);
PreorderTraverseLeaves(rootNode->right);
}
}
void TreeType::InorderTraverseLeaves(TreeNode *rootNode) {
if(rootNode!=NULL) {
InorderTraverseLeaves(rootNode->left);
if ((rootNode->left == NULL) && (rootNode->right == NULL)) {
std::cout << rootNode->info << " ";
}
InorderTraverseLeaves(rootNode->right);
}
}
void TreeType::PostorderTraverseLeaves(TreeNode *rootNode) {
if(rootNode!=NULL)
{
PostorderTraverseLeaves(rootNode->left);
PostorderTraverseLeaves(rootNode->right);
if ((rootNode->left == NULL) && (rootNode->right == NULL)) {
std::cout << rootNode->info << " ";
}
}
}
----------------------------------------------main.cpp------------------------------------------
main.cpp
std::cout << endl;
std::cout << "LeavesNum: " << endl;
int lnum = 0;
binarySearchTree.LeavesNum(binarySearchTree.root, lnum);
std::cout << "LeavesNum: " << lnum << endl;
std::cout << "PreorderTraverseLeaves: " << endl;
binarySearchTree.PreorderTraverseLeaves(binarySearchTree.root);
std::cout << endl;
std::cout << "InorderTraverseLeaves: " << endl;
binarySearchTree.InorderTraverseLeaves(binarySearchTree.root);
std::cout << endl;
std::cout << "PostorderTraverseLeaves: " << endl;
binarySearchTree.PostorderTraverseLeaves(binarySearchTree.root);
std::cout << endl;
输出结果如下:
64.8 删除二叉查找树中某个结点
删除某个结点,步骤如下:
1,在二叉查找树中找到该结点;
2,将该结点的父结点对应的左孩子或者右孩子的指针设为空;
3,删除以该结点为根结点的子树;
比如,若删除结点“45”,则是下图中蓝色圈内的4个结点。
C++代码如下:
----------------------------------------------TreeType.h------------------------------------------
TreeType.h
bool DeleteItem(TreeNode *rootNode, ItemType item);
----------------------------------------------TreeType.cpp------------------------------------------
TreeType.cpp
void DeleteTree(TreeNode *rootNode) {
if (rootNode == NULL) {
}
else {
TreeNode *temp_left = rootNode->left;
TreeNode *temp_right = rootNode->right;
delete rootNode;
if (temp_left != NULL) {
DeleteTree(temp_left);
}
if (temp_right != NULL) {
DeleteTree(temp_right);
}
}
}
bool TreeType::DeleteItem(TreeNode *rootNode, ItemType item) {
if (rootNode == NULL) {
return false;
}
else {
if (rootNode->left != NULL) {
if (rootNode->left->info == item) {
DeleteTree(rootNode->left);
rootNode->left = NULL;
return true;
}
}
if (rootNode->right != NULL) {
if (rootNode->right->info == item) {
DeleteTree(rootNode->right);
rootNode->right = NULL;
return true;
}
}
if (DeleteItem(rootNode->left, item)) {
return true;
}
if (DeleteItem(rootNode->right, item)) {
return true;
}
else {
return false;
}
}
}
----------------------------------------------main.cpp------------------------------------------
main.cpp
/*先删除结点“45”(即以该结点为根结点的子树)。然后在遍历完成删除动作后剩余的树,同时计算剩余结点数,和剩余叶子结点数,再遍历叶子结点*/
std::cout << endl;
item = 45;
std::cout << "DeleteItem: " << item << endl;
bool deleted = binarySearchTree.DeleteItem(binarySearchTree.root, item);
std::cout << "deleted: " << deleted << endl;
std::cout << endl;
std::cout << "PreorderTraverse: " << endl;
binarySearchTree.PreorderTraverse(binarySearchTree.root);
std::cout << endl;
std::cout << "InorderTraverse: " << endl;
binarySearchTree.InorderTraverse(binarySearchTree.root);
std::cout << endl;
std::cout << "PostorderTraverse: " << endl;
binarySearchTree.PostorderTraverse(binarySearchTree.root);
std::cout << endl;
std::cout << endl;
std::cout << "NodesNum: " << endl;
num = binarySearchTree.NodesNum(binarySearchTree.root);
std::cout << "NodesNum: " << num << endl;
std::cout << endl;
std::cout << "LeavesNum: " << endl;
lnum = 0;
binarySearchTree.LeavesNum(binarySearchTree.root, lnum);
std::cout << "LeavesNum: " << lnum << endl;
std::cout << "PreorderTraverseLeaves: " << endl;
binarySearchTree.PreorderTraverseLeaves(binarySearchTree.root);
std::cout << endl;
std::cout << "InorderTraverseLeaves: " << endl;
binarySearchTree.InorderTraverseLeaves(binarySearchTree.root);
std::cout << endl;
std::cout << "PostorderTraverseLeaves: " << endl;
binarySearchTree.PostorderTraverseLeaves(binarySearchTree.root);
std::cout << endl;
输出结果如下:
64.9 C++代码汇总
----------------------------------------------TreeType.h------------------------------------------
TreeType.h
#ifndef TREETYPE_H
#define TREETYPE_H
#include <iostream>
using namespace std;
typedef int ItemType;
struct TreeNode
{
ItemType info;
TreeNode* left;
TreeNode* right;
};
class TreeType {// binary search tree.
public:
TreeType() {
root = NULL;
}
void CreateTree(ItemType *itemArray, int itemNum);
void PreorderTraverse(TreeNode *rootNode);
void InorderTraverse(TreeNode *rootNode);
void PostorderTraverse(TreeNode *rootNode);
void InsertItems(ItemType *itemArray, int itemNum);
bool FindItem(TreeNode *rootNode, ItemType item);
ItemType MinValue(TreeNode *rootNode);
ItemType MaxValue(TreeNode *rootNode);
int NodesNum(TreeNode *rootNode);
void LeavesNum(TreeNode *rootNode, int &num);
void PreorderTraverseLeaves(TreeNode *rootNode);
void InorderTraverseLeaves(TreeNode *rootNode);
void PostorderTraverseLeaves(TreeNode *rootNode);
bool DeleteItem(TreeNode *rootNode, ItemType item);
TreeNode *root;
};
#endif // TREETYPE_H
----------------------------------------------TreeType.cpp------------------------------------------
TreeType.cpp
#include "TreeType.h"
void TreeType::CreateTree(ItemType *itemArray, int itemNum) {
for(int i=0; i<itemNum; i++) {
TreeNode *newnode = new TreeNode;
newnode->info = itemArray[i];
newnode->left = NULL;
newnode->right = NULL;
if(root == NULL) {
root = newnode;
std::cout << itemArray[i] << " will be the root" << endl;
}
else {
TreeNode *parent;
TreeNode *temp = root;
while(temp != NULL) {
parent = temp;
if((temp->info) > itemArray[i]) {
temp = temp->left;
}
else {
temp = temp->right;
}
}
if((parent->info) > itemArray[i]) {
parent->left = newnode;
std::cout << itemArray[i] << " will be " << parent->info << "'s left child" << endl;
}
else {
parent->right = newnode;
std::cout << itemArray[i] << " will be " << parent->info << "'s right child" << endl;
}
}
}
}
void TreeType::PreorderTraverse(TreeNode *rootNode) {
if(rootNode!=NULL)
{
std::cout << rootNode->info << " ";
PreorderTraverse(rootNode->left);
PreorderTraverse(rootNode->right);
}
}
void TreeType::InorderTraverse(TreeNode *rootNode) {
if(rootNode!=NULL)
{
InorderTraverse(rootNode->left);
std::cout << rootNode->info << " ";
InorderTraverse(rootNode->right);
}
}
void TreeType::PostorderTraverse(TreeNode *rootNode) {
if(rootNode!=NULL)
{
PostorderTraverse(rootNode->left);
PostorderTraverse(rootNode->right);
std::cout << rootNode->info << " ";
}
}
void TreeType::InsertItems(ItemType *itemArray, int itemNum) {
for(int i=0; i<itemNum; i++) {
TreeNode *newnode = new TreeNode;
newnode->info = itemArray[i];
newnode->left = NULL;
newnode->right = NULL;
if(root == NULL) {
root = newnode;
std::cout << itemArray[i] << " will be the root" << endl;
}
else {
TreeNode *parent;
TreeNode *temp = root;
while(temp != NULL) {
parent = temp;
if((temp->info) > itemArray[i]) {
temp = temp->left;
}
else if((temp->info) == itemArray[i]) {
break;
}
else {
temp = temp->right;
}
}
if((parent->info) > itemArray[i]) {
parent->left = newnode;
std::cout << itemArray[i] << " will be " << parent->info << "'s left child" << endl;
}
else if((parent->info) == itemArray[i]) {
std::cout << "there has been a " << itemArray[i] << " in the tree" << endl;
}
else {
parent->right = newnode;
std::cout << itemArray[i] << " will be " << parent->info << "'s right child" << endl;
}
}
}
}
bool TreeType::FindItem(TreeNode *rootNode, ItemType item) {
if (rootNode == NULL) {
return false;
}
else {
if ((rootNode->info) == item) {
std::cout << "found." << endl;
if ((rootNode->left) != NULL) {
std::cout << "its left child is " << rootNode->left->info << " ." << endl;
}
if ((rootNode->right) != NULL) {
std::cout << "its right child is " << rootNode->right->info << " ." << endl;
}
return true;
}
else {
if (FindItem(rootNode->left, item)) {
return true;
}
if (FindItem(rootNode->right, item)) {
return true;
}
return false;
}
}
}
ItemType TreeType::MinValue(TreeNode *rootNode) {
if(rootNode!=NULL)
{
if ((rootNode->left) != NULL) {
MinValue(rootNode->left);
}
else {
return rootNode->info;
}
}
}
ItemType TreeType::MaxValue(TreeNode *rootNode) {
if(rootNode!=NULL)
{
if ((rootNode->right) != NULL) {
MaxValue(rootNode->right);
}
else {
return rootNode->info;
}
}
}
int TreeType::NodesNum(TreeNode *rootNode) {
if(rootNode!=NULL)
{
return (NodesNum(rootNode->left) + NodesNum(rootNode->right) + 1);
}
else {
return 0;
}
}
void TreeType::LeavesNum(TreeNode *rootNode, int &num) {
if(rootNode!=NULL)
{
if (((rootNode->left) == NULL) && ((rootNode->right) == NULL)) {
num ++;
}
else {
LeavesNum(rootNode->left, num);
LeavesNum(rootNode->right, num);
}
}
}
void TreeType::PreorderTraverseLeaves(TreeNode *rootNode) {
if(rootNode!=NULL) {
if ((rootNode->left == NULL) && (rootNode->right == NULL)) {
std::cout << rootNode->info << " ";
}
PreorderTraverseLeaves(rootNode->left);
PreorderTraverseLeaves(rootNode->right);
}
}
void TreeType::InorderTraverseLeaves(TreeNode *rootNode) {
if(rootNode!=NULL) {
InorderTraverseLeaves(rootNode->left);
if ((rootNode->left == NULL) && (rootNode->right == NULL)) {
std::cout << rootNode->info << " ";
}
InorderTraverseLeaves(rootNode->right);
}
}
void TreeType::PostorderTraverseLeaves(TreeNode *rootNode) {
if(rootNode!=NULL)
{
PostorderTraverseLeaves(rootNode->left);
PostorderTraverseLeaves(rootNode->right);
if ((rootNode->left == NULL) && (rootNode->right == NULL)) {
std::cout << rootNode->info << " ";
}
}
}
void DeleteTree(TreeNode *rootNode) {
if (rootNode == NULL) {
}
else {
TreeNode *temp_left = rootNode->left;
TreeNode *temp_right = rootNode->right;
delete rootNode;
if (temp_left != NULL) {
DeleteTree(temp_left);
}
if (temp_right != NULL) {
DeleteTree(temp_right);
}
}
}
bool TreeType::DeleteItem(TreeNode *rootNode, ItemType item) {
if (rootNode == NULL) {
return false;
}
else {
if (rootNode->left != NULL) {
if (rootNode->left->info == item) {
DeleteTree(rootNode->left);
rootNode->left = NULL;
return true;
}
}
if (rootNode->right != NULL) {
if (rootNode->right->info == item) {
DeleteTree(rootNode->right);
rootNode->right = NULL;
return true;
}
}
if (DeleteItem(rootNode->left, item)) {
return true;
}
if (DeleteItem(rootNode->right, item)) {
return true;
}
else {
return false;
}
}
}
----------------------------------------------main.cpp------------------------------------------
main.cpp
#include <iostream>
#include <fstream>
#include <limits>
#include <stdlib.h>
#include <TreeType.h>
using namespace std;
int main()
{
TreeType binarySearchTree;
ItemType infoArray[15] = {20, 12, 2, 14, 15, 35, 6, 45, 25, 23, 1, 24, 16, 57, 28};
std::cout << "CreateTree: " << endl;
binarySearchTree.CreateTree(infoArray, 15);
std::cout << endl;
std::cout << "PreorderTraverse: " << endl;
binarySearchTree.PreorderTraverse(binarySearchTree.root);
std::cout << endl;
std::cout << "InorderTraverse: " << endl;
binarySearchTree.InorderTraverse(binarySearchTree.root);
std::cout << endl;
std::cout << "PostorderTraverse: " << endl;
binarySearchTree.PostorderTraverse(binarySearchTree.root);
std::cout << endl;
std::cout << endl;
ItemType insertItems[4] = {40, 32, 42, 28};
std::cout << "InsertItems: ";
for (int i=0; i<4; i++) {
std::cout << insertItems[i] << " ";
}
std::cout << endl;
binarySearchTree.InsertItems(insertItems, 4);
std::cout << endl;
std::cout << "PreorderTraverse: " << endl;
binarySearchTree.PreorderTraverse(binarySearchTree.root);
std::cout << endl;
std::cout << "InorderTraverse: " << endl;
binarySearchTree.InorderTraverse(binarySearchTree.root);
std::cout << endl;
std::cout << "PostorderTraverse: " << endl;
binarySearchTree.PostorderTraverse(binarySearchTree.root);
std::cout << endl;
std::cout << endl;
ItemType item = 35;
bool found;
std::cout << "FindItem: " << item << endl;
found = binarySearchTree.FindItem(binarySearchTree.root, item);
std::cout << "found: " << found << endl;
std::cout << endl;
std::cout << "MinValue: " << endl;
ItemType minItem = binarySearchTree.MinValue(binarySearchTree.root);
std::cout << "minItem: " << minItem << endl;
std::cout << endl;
std::cout << "MaxValue: " << endl;
ItemType maxItem = binarySearchTree.MaxValue(binarySearchTree.root);
std::cout << "maxItem: " << maxItem << endl;
std::cout << endl;
std::cout << "NodesNum: " << endl;
int num = binarySearchTree.NodesNum(binarySearchTree.root);
std::cout << "NodesNum: " << num << endl;
std::cout << endl;
std::cout << "LeavesNum: " << endl;
int lnum = 0;
binarySearchTree.LeavesNum(binarySearchTree.root, lnum);
std::cout << "LeavesNum: " << lnum << endl;
std::cout << "PreorderTraverseLeaves: " << endl;
binarySearchTree.PreorderTraverseLeaves(binarySearchTree.root);
std::cout << endl;
std::cout << "InorderTraverseLeaves: " << endl;
binarySearchTree.InorderTraverseLeaves(binarySearchTree.root);
std::cout << endl;
std::cout << "PostorderTraverseLeaves: " << endl;
binarySearchTree.PostorderTraverseLeaves(binarySearchTree.root);
std::cout << endl;
std::cout << endl;
item = 45;
std::cout << "DeleteItem: " << item << endl;
bool deleted = binarySearchTree.DeleteItem(binarySearchTree.root, item);
std::cout << "deleted: " << deleted << endl;
std::cout << endl;
std::cout << "PreorderTraverse: " << endl;
binarySearchTree.PreorderTraverse(binarySearchTree.root);
std::cout << endl;
std::cout << "InorderTraverse: " << endl;
binarySearchTree.InorderTraverse(binarySearchTree.root);
std::cout << endl;
std::cout << "PostorderTraverse: " << endl;
binarySearchTree.PostorderTraverse(binarySearchTree.root);
std::cout << endl;
std::cout << endl;
std::cout << "NodesNum: " << endl;
num = binarySearchTree.NodesNum(binarySearchTree.root);
std::cout << "NodesNum: " << num << endl;
std::cout << endl;
std::cout << "LeavesNum: " << endl;
lnum = 0;
binarySearchTree.LeavesNum(binarySearchTree.root, lnum);
std::cout << "LeavesNum: " << lnum << endl;
std::cout << "PreorderTraverseLeaves: " << endl;
binarySearchTree.PreorderTraverseLeaves(binarySearchTree.root);
std::cout << endl;
std::cout << "InorderTraverseLeaves: " << endl;
binarySearchTree.InorderTraverseLeaves(binarySearchTree.root);
std::cout << endl;
std::cout << "PostorderTraverseLeaves: " << endl;
binarySearchTree.PostorderTraverseLeaves(binarySearchTree.root);
std::cout << endl;
}
输出结果如下: