C++实现二叉树基本操作详解
二叉树是计算机科学中的重要数据结构,其实现在C++编程中是必不可少的。本文将从二叉树的定义、基本操作的实现以及示例说明三个方面,详细讲解如何在C++中实现二叉树。
一、二叉树的定义
二叉树是一种树形结构,其中每个节点最多只包含两个子节点(左子节点和右子节点)。每个节点都包含一个值(或者说是一个数据项),而左右子节点则分别指向另外两个节点,或者为nullptr
。下图展示了一个典型的二叉树结构:
1
/ \
2 3
/ \
4 5
在上述示例中,节点1是二叉树的根节点,而其左子节点为2、右子节点为3。同样,节点2的左子节点为4、右子节点为5。
二、二叉树的基本操作
1. 插入节点
要向二叉树中插入一个新的节点,首先需要判断这个新节点是在左子树中插入还是在右子树中插入。如果刚好没有该节点,则可以直接插入;如果存在该节点,则需要对该节点进行更新。
下面是向二叉树中插入新节点的示例代码:
// 在二叉搜索树中插入一个新节点
// @param root: 二叉树的根节点
// @param data: 新节点的值
void insert(TreeNode*& root, int data) {
if(root == nullptr) {
root = new TreeNode(data);
return;
}
if(data < root->val) {
insert(root->left, data);
}
else if(data > root->val) {
insert(root->right, data);
}
// 如果相等,则说明节点已经存在
}
上述代码中,TreeNode
类表示二叉树的节点,其中包含一个整数值val
、左子节点left
和右子节点right
。在insert
函数中,首先判断二叉树是否为空,如果是,则将新节点作为根节点。如果二叉树不为空,则从根节点开始,递归地向左子树或右子树中插入新节点。
2. 遍历树
二叉树可以通过三种方式进行遍历:前序遍历、中序遍历和后序遍历。在前序遍历中,首先访问根节点,然后按照左子节点、右子节点的顺序访问下一个节点。在中序遍历中,首先访问左子节点,然后访问根节点,最后访问右子节点。在后序遍历中,首先访问左子节点,然后访问右子节点,最后访问根节点。
下面是前序遍历的示例代码:
// 前序遍历二叉树
// @param root: 二叉树的根节点
void preOrder(TreeNode* root) {
if(root == nullptr) {
return;
}
cout << root->val << " ";
preOrder(root->left);
preOrder(root->right);
}
在上述代码中,先输出当前节点的值,然后递归遍历左子树和右子树。
3. 删除节点
要删除二叉树中的一个节点,首先需要找到该节点。如果该节点没有子节点,则可以直接删除。如果该节点有一个子节点,则需要将该节点的父节点指向子节点。如果该节点有两个子节点,则需要将该节点的右子树中的最小节点拿来替换该节点。
下面是删除二叉树节点的示例代码:
// 删除节点
// @param root: 二叉树的根节点
// @param data: 要删除的节点的值
// @return: 新的根节点
TreeNode* remove(TreeNode* root, int data) {
if(root == nullptr) {
return nullptr;
}
if(data < root->val) {
root->left = remove(root->left, data);
}
else if(data > root->val) {
root->right = remove(root->right, data);
}
else {
// 找到要删除的节点
if(root->left == nullptr) {
TreeNode* rightNode = root->right;
delete root;
return rightNode;
}
if(root->right == nullptr) {
// 可以省略rightNode,直接return root->left
TreeNode* leftNode = root->left;
delete root;
return leftNode;
}
// 用右子树中的最小值节点,替换要删除的节点
TreeNode* minRightNode = getMinNode(root->right);
root->val = minRightNode->val;
root->right = remove(root->right, minRightNode->val);
}
return root;
}
// 获取根节点为node的树的最小节点
// @param node: 节点
TreeNode* getMinNode(TreeNode* node) {
while(node->left != nullptr) {
node = node->left;
}
return node;
}
在上述代码中,getMinNode
函数用于获取从指定节点开始的子树中的最小值节点。在remove
函数中,首先通过recursion
找到要删除的节点。然后,如果该节点为叶子节点或只有一个子节点,直接删除该节点并返回另一个子节点。如果该节点有两个子节点,找到其右子树中的最小值节点,然后用该节点替换要删除的节点,再递归删除该节点。
三、示例说明
下面通过两个示例,展示了如何在C++中实现二叉树的基本操作。
1. 在二叉搜索树中查找元素
// 判断二叉搜索树中是否包含指定元素
// @param root: 二叉树的根节点
// @param data: 指定元素的值
// @return: 是否包含指定元素
bool contains(TreeNode* root, int data) {
if (root == nullptr) {
return false;
}
if (root->val == data) {
return true;
}
else if (data < root->val) {
return contains(root->left, data);
}
else {
return contains(root->right, data);
}
}
int main() {
TreeNode* root = nullptr;
insert(root, 5);
insert(root, 2);
insert(root, 7);
insert(root, 1);
insert(root, 3);
cout << contains(root, 3) << endl; // true
cout << contains(root, 8) << endl; // false
}
在上述代码中,首先创建一个二叉搜索树,然后使用contains
函数判断该树中是否包含3和8两个元素,结果分别为true
和false
。
2. 删除二叉搜索树中的一个节点
int main() {
TreeNode* root = nullptr;
insert(root, 5);
insert(root, 2);
insert(root, 7);
insert(root, 1);
insert(root, 3);
cout << "Before remove: ";
preOrder(root); // 5 2 1 3 7
cout << endl;
root = remove(root, 2);
cout << "After remove: ";
preOrder(root); // 5 3 1 7
cout << endl;
}
在上述代码中,首先创建一个二叉搜索树,并在其中插入了5、2、7、1和3这些节点。然后,使用preOrder
函数遍历该树。接下来,删除值为2的节点,并使用preOrder
函数遍历树。
在删除节点后,遍历的结果变成了5、3、1和7。
本站文章如无特殊说明,均为本站原创,如若转载,请注明出处:C++实现二叉树基本操作详解 - Python技术站