二叉搜索树(BST)和二叉平衡树(AVL)
二叉搜索树(BST)
在二叉搜索树(又称二叉排序树或者二叉查找树)中:
- 若任意结点的左子树不空,则左子树上所有结点的值均不大于它的根结点的值;
- 若任意结点的右子树不空,则右子树上所有结点的值均不小于它的根结点的值;
- 任意结点的左、右子树也分别为二叉搜索树。
基本操作和代码实现
树的节点
class Node {
Integer data;
Node left;
Node right;
Node parent;
public Node(Integer data, Node left, Node right, Node parent) {
this.data = data;
this.left = left;
this.right = right;
this.parent = parent;
}
}
最小关键字
最小关键字查询过程:根据二叉搜索树性质,左子树小于该节点。从根节点开始,一直找left指针,直到left指针为null。
public Node getMin(Node root) {
if (root == null) {
return null;
}
while (root.left != null) {
root = root.left;
}
return root;
}
最大关键字
最大关键字查询过程:根据二叉搜索树性质,右子树大于该节点。从根节点开始,一直找right指针,直到right指针为null。
public Node getMax(Node root) {
if (root == null) {
return null;
}
while (root.right != null) {
root = root.right;
}
return root;
}
查找
查找某关键字的过程为:
- 树根开始查找,若根为null,则查找失败,返回NULL;
- 如果根节点的值等于关键字,返回根节点,结束查找;
- 如果根节点的值小于关键字,继续查找根节点的左子树;
- 如果根节点的值大于关键字,继续查找根节点的右子树;
- 如果查找到叶子节点仍不相等,关键字不存在,返回NULL,结束查找。
/**
* 查找值为data的节点(递归)
* @param root
* @param data
* @return
*/
public Node searchRec(Node root, int data) {
if (root == null) {
return null;
}
if (root.data > data) {
return searchRec(root.left, data);
} else if (root.data < data) {
return searchRec(root.right, data);
} else {
return root;
}
}
/**
* 查找值为data的节点
* @param root
* @param data
* @return
*/
public Node search(Node root, int data) {
while (root != null) {
if (root.data > data) {
root = root.left;
} else if (root.data < data) {
root = root.right;
} else {
break;
}
}
return root;
}
插入节点
插入节点的过程:
- 新值v插入到一棵二叉搜索树T中,新建一个结点tmp;
- 从根节点开始,如果值v大于根节点,查找其右子树;
- 如果值v小于根节点,查找其左子树;
- 当某个节点的左子树或右子树为null时,这个null的位置即为要插入节点tmp的位置。
- 如果在查找过程中,发现值v等于某个节点的值,证明该值已经存在于树中,插入结束。
/**
* BST插入节点(递归)
*
* @param root
* @param insert
* @return
*/
public Node insertRec(Node root, Node insert) {
if (root == null) {
root = insert;
} else if (root.data > insert.data) {
root.left = insertRec(root.left, insert);
} else if (root.data < insert.data) {
root.right = insertRec(root.right, insert