//BinaraTree.h
#pragma once
#include <iostream>
using namespace std;
//升序二叉树
//左节点 < 根节点 < 右节点
struct Node
{
Node *pLeft;//左节点
Node *pRight;//右节点
int data;//数值
};
class BinaryTree
{
public:
BinaryTree();
~BinaryTree();
Node* createNode(int data);//创建节点
//Node* searchNode(Node *root, int data);//查找data需要插入的位置并返回
void insertData(int data);//插入数值,调用类中的insertNode函数来将data插入到pRoot的位置
//需要改变pRoot中的值,其之前指向的是null,需要改变其指向故需要传二级指针
void insertNode(Node **root, int data);//在某个位置插入数值data
void Traver();//遍历,调用preTraver,来从pRoot开始遍历
void preTraver(Node *root);//前序遍历,其他遍历都是同样思路
//将被删除点的左孩子成为其右孩子的最左节点
bool deleteNode(const int data);
private:
Node *pRoot;
};
//BinaryTree.cpp
#include "BinaryTree.h"
BinaryTree::BinaryTree()
{
pRoot = nullptr;
}
BinaryTree::~BinaryTree()
{
}
Node * BinaryTree::createNode(int data)
{
Node *pNew = new Node;
pNew->data = data;
pNew->pLeft = nullptr;
pNew->pRight = nullptr;
return pNew;
}
#if 0
//递归来实现
Node * BinaryTree::searchNode(Node * root, int data)
{
//终止条件是节点为null
if (!root)
return root;
if (data < root->data)
searchNode(root->pLeft, data);
else
searchNode(root->pRight, data);
}
#endif
void BinaryTree::insertData(int data)
{
insertNode(&pRoot, data);
}
void BinaryTree::insertNode(Node **root, int data)
{
if (!*root)
{
Node *tmp = createNode(data);
*root = tmp;
return;
}
if (data < (*root)->data)
insertNode(&(*root)->pLeft, data);
else
insertNode(&(*root)->pRight, data);
}
void BinaryTree::Traver()
{
//前序遍历
preTraver(pRoot);
}
void BinaryTree::preTraver(Node *root)
{
if (!root)
return;
preTraver(root->pLeft);
cout << root->data << " ";
preTraver(root->pRight);
}
bool BinaryTree::deleteNode(const int data)
{
Node *pTemp = nullptr;
Node *pDel = pRoot;
Node *pDelParent = pRoot;
//删除的是根节点
if (pRoot->data == data)
{
//有右孩子,则左孩子成为右孩子的最左孩子
if (pRoot->pRight)
{
pTemp = pRoot->pRight;
//找到根节点右孩子的最左节点
while (pTemp->pLeft)
{
pTemp = pTemp->pLeft;
}
pTemp->pLeft = pRoot->pLeft;
pRoot = pDel->pRight;//pRoot指向其右孩子
}
else
{
pRoot = pRoot->pLeft;
}
delete pDel;
pDel = nullptr;
return true;
}
//删除的不是根节点
else
{
bool bIsFind = false;//判断是否找到data
//找到pDel的父节点
while (pDel)
{
if (pDel->data == data)
{
bIsFind = true;
break;
}
pDelParent = pDel;
if (pDel->data < data)
pDel = pDel->pRight;
else
pDel = pDel->pLeft;
}
//未找到data
if (!bIsFind)
return false;
//pDel有右孩子,让pDel的左节点成为pDel的右孩子的最左孩子
if (pDel->pRight)
{
pTemp = pDel->pRight;
// 找到最左孩子
while (pTemp->pLeft)
{
pTemp = pTemp->pLeft;
}
pTemp->pLeft = pDel->pLeft;
//pDel是pDelParent的右孩子
if (pDel == pDelParent->pRight)
{
//pDel的右孩子成为pDelParent的右孩子
pDelParent->pRight = pDel->pRight;
}
else
{
pDelParent->pLeft = pDel->pRight;
}
}
//没有右孩子
else
{
//pDel是pDelParent的右孩子
if (pDel == pDelParent->pRight)
{
pDelParent->pRight = pDel->pLeft;
}
else
{
//pDel是pDelParaent的左孩子
pDelParent->pLeft = pDel->pLeft;
}
}
delete pDel;
pDel = nullptr;
return true;
}
}
//main.cpp
#include "BinaryTree.h"
int main()
{
BinaryTree tree;
tree.insertData(20);
tree.insertData(10);
tree.insertData(100);
tree.insertData(1);
tree.insertData(88);
tree.insertData(15);
tree.insertData(70);
tree.Traver();
cout << endl;
cout << "after delete:" << std::endl;
tree.deleteNode(88);
tree.Traver();
return 0;
}