目录
1.二叉查找树的定义
在WikiPedia中,对二叉查找树的定义如下。
二叉查找树,是一种基于节点的二叉树,有下面的性质:
- 节点的左子树中任意节点值小于根节点
- 节点的右子树中任意节点值大于根节点
- 左右子树都必须是二叉查找树,不允许存在重复节点。
二叉查找树的上述性质,保证了各节点值的顺序,这样进行查找,求最大值最小值时,效率会更高。如果没有这种顺序,则可能需要将树中的每个节点与指定的查找值进行比较。
2.查找一个节点值
二叉树中查找一个节点值时,首先与根节点比较,相等则返回根节点。如果根节点小于指定值,则递归的查找右子树。否则查找左子树。
//在二叉搜索树中查找特定的值
Node* search(Node* root, int key) {
// Base Cases: 空树或者值为根节点值
if (root == NULL || root->key == key)
return root;
// 指定值大于根值
if (root->key < key)
return search(root->right, key);
// 指定值小于根植
return search(root->left, key);
}
3.插入一个节点值
新的值常常做为叶子节点插入到树中。首先从根节点开始,直到遇到叶子节点为止。一旦找到了叶子节点,则将新的值做为叶子节点的一个孩子。
100 100
/ \ Insert 40 / \
20 500 ---------------------> 20 500
/ \ / \
10 30 10 30
\
40
代码实现如下。
#include <iostream>
struct Node {
int key;
Node *left;
Node *right;
};
// 创建一个新的BST节点
Node *createNewNode(int item) {
Node *temp = new Node;
temp->key = item;
temp->left = temp->right = NULL;
return temp;
}
// 中序遍历二叉搜索树
void inorder(Node *root) {
if (root != NULL) {
inorder(root->left);
std::cout<<" "<<root->key<<" ";
inorder(root->right);
}
}
//插入新节点至二叉搜索树中
Node* insert(Node* node, int key) {
//空树
if (node == NULL)
return createNewNode(key);
//递归插入。如果已存在指定值,则不插入
if (key < node->key)
node->left = insert(node->left, key);
else if (key > node->key)
node->right = insert(node->right, key);
//返回未修改的node指针
return node;
}
int main() {
//构建如上面所示的一棵树
Node *root = NULL;
root = insert(root, 50);
insert(root, 30);
insert(root, 20);
insert(root, 40);
insert(root, 70);
insert(root, 60);
insert(root, 80);
// 中序遍历
inorder(root);
return 0;
}
运行结果:
20 30 40 50 60 70 80
时间复杂度:最差的查找以及插入操作的时间复杂度为O(h),其中h是树的高度。在最差情况下,可能需要从根节点一直遍历到叶子节点。