一切具有层次关系的问题可以用树来描述,树结构对数据信息进行分类分层管理,是非线性的结构。解决实际问题——图书管理、文件系统、组织架构和族谱等等,树的结构具有很高的效率。
树的定义和基本术语:
定义:树是包含n个节点的有限集合。
根节点:开始结点,root,只有直接后继,没有直接前驱。
空树:n=0,没有节点。
叶节点:没有子节点的节点。
度:一个节点的子树个数。树的度为根节点的度。
深度:树的最大层数,也称树的高度。
有序树:每个节点的子树都是从左到右有序的。
森林:互不相交树的集合。树删除根节点变成树,森林加一个根节点变成树。
路径:追根溯源的道路。
关于树的操作:
构造、查找、插入、删除、遍历、求深度等
构造方式通常使用链式存储方式,能够动态分配内存。
遍历:递归方式进行,先序(父左右)、中序(左父右)、后序(左右父)遍历根据父节点的先、中、后遍历定义的。
#include <iostream>
// 二叉树节点
struct TreeNode {
int data;
TreeNode* left;
TreeNode* right;
TreeNode(int val) : data(val), left(nullptr), right(nullptr) {}
};
// 二叉搜索树类
class BinarySearchTree {
private:
TreeNode* root;
// 插入辅助函数
TreeNode* insertHelper(TreeNode* node, int value) {
if (node == nullptr) {
return new TreeNode(value);
}
if (value < node->data) {
node->left = insertHelper(node->left, value);
} else if (value > node->data) {
node->right = insertHelper(node->right, value);
}
return node;
}
// 查找辅助函数
TreeNode* findHelper(TreeNode* node, int value) const {
if (node == nullptr || node->data == value) {
return node;
}
if (value < node->data) {
return findHelper(node->left, value);
} else {
return findHelper(node->right, value);
}
}
// 删除辅助函数
TreeNode* deleteHelper(TreeNode* node, int value) {
if (node == nullptr) {
return nullptr;
}
if (value < node->data) {
node->left = deleteHelper(node->left, value);
} else if (value > node->data) {
node->right = deleteHelper(node->right, value);
} else {
// 找到待删除节点
// 情况 1: 无子节点或仅有一个子节点
if (node->left == nullptr) {
TreeNode* temp = node->right;
delete node;
return temp;
} else if (node->right == nullptr) {
TreeNode* temp = node->left;
delete node;
return temp;
}
// 情况 2: 有两个子节点,找到右子树中最小的节点替换当前节点
TreeNode* temp = minValueNode(node->right);
node->data = temp->data;
node->right = deleteHelper(node->right, temp->data);
}
return node;
}
// 查找最小值辅助函数
TreeNode* minValueNode(TreeNode* node) {
TreeNode* current = node;
while (current->left != nullptr) {
current = current->left;
}
return current;
}
// 先序遍历辅助函数
void preorderTraversalHelper(TreeNode* node) const {
if (node != nullptr) {
std::cout << node->data << " ";
preorderTraversalHelper(node->left);
preorderTraversalHelper(node->right);
}
}
// 中序遍历辅助函数
void inorderTraversalHelper(TreeNode* node) const {
if (node != nullptr) {
inorderTraversalHelper(node->left);
std::cout << node->data << " ";
inorderTraversalHelper(node->right);
}
}
// 后序遍历辅助函数
void postorderTraversalHelper(TreeNode* node) const {
if (node != nullptr) {
postorderTraversalHelper(node->left);
postorderTraversalHelper(node->right);
std::cout << node->data << " ";
}
}
// 求深度辅助函数
int depthHelper(TreeNode* node) const {
if (node == nullptr) {
return 0;
}
int leftDepth = depthHelper(node->left);
int rightDepth = depthHelper(node->right);
return 1 + std::max(leftDepth, rightDepth);
}
public:
// 构造函数
BinarySearchTree() : root(nullptr) {}
// 插入
void insert(int value) {
root = insertHelper(root, value);
}
// 查找
bool find(int value) const {
return findHelper(root, value) != nullptr;
}
// 删除
void remove(int value) {
root = deleteHelper(root, value);
}
// 先序遍历
void preorderTraversal() const {
std::cout << "Preorder Traversal: ";
preorderTraversalHelper(root);
std::cout << "\n";
}
// 中序遍历
void inorderTraversal() const {
std::cout << "Inorder Traversal: ";
inorderTraversalHelper(root);
std::cout << "\n";
}
// 后序遍历
void postorderTraversal() const {
std::cout << "Postorder Traversal: ";
postorderTraversalHelper(root);
std::cout << "\n";
}
// 求深度
int depth() const {
return depthHelper(root);
}
// 析构函数,释放内存
~BinarySearchTree() {
delete root;
}
};
int main() {
BinarySearchTree bst;
// 插入元素
bst.insert(50);
bst.insert(30);
bst.insert(20);
bst.insert(40);
bst.insert(70);
bst.insert(60);
bst.insert(80);
// 遍历
bst.preorderTraversal();
bst.inorderTraversal();
bst.postorderTraversal();
// 查找
std::cout << "Find 30: " << (bst.find(30) ? "Found" : "Not Found") << "\n";
// 删除
bst.remove(30);
// 遍历
bst.preorderTraversal();
bst.inorderTraversal();
bst.postorderTraversal();
// 查找
std::cout << "Find 30: " << (bst.find(30) ? "Found" : "Not Found") << "\n";
// 求深度
std::cout << "Tree Depth: " << bst.depth() << "\n";
return 0;
}