二叉搜索树:根节点的值大于其左子树中任意一个节点的值,小于其右节点中任意一节点的值。进行中序遍历得到一个递增的序列
代码实现
class BinarySearchTree {
BSTNode root;
static class BSTNode {
public int val;
public BSTNode left;
public BSTNode right;
public BSTNode(int val) {
this.val = val;
}
}
}
查找节点
//查找节点
public BSTNode find(int val) {
if (root == null) return null;
BSTNode cur = root;
while (cur != null) {
if (cur.val > val) {
cur = cur.left;
} else if (cur.val < val) {
cur = cur.right;
} else {
return cur;
}
}
return null;
}
根据二叉搜索树本身的性质查找节点,和根比较大小,大于根节点在右子树中查找,小于根节点在左子树中查找,找到返回要查找的节点,反之返回null
插入节点
public boolean insert(int val) {
BSTNode node = new BSTNode(val);
if (root == null) {
root = node;
return true;
} else {
BSTNode cur = root;
BSTNode pre = null;
while (cur != null) {
pre = cur;
if (cur.val > val) {
cur = cur.left;
} else if (cur.val < val) {
cur = cur.right;
} else {
return false;
}
}
if (pre.val > val) {
pre.left = node;
} else {
pre.right = node;
}
return true;
}
}
用待插入的值和根先比较,若根为空则将此节点作为根;不为空则根据根结点的大小确认待插入的位置,若待插入的值小于根节点的值,则向左子树中寻找位置,大于根节点的值则向右子树中查找,找到合适的位置插入即可
删除节点
删除节点后,此树还是二叉搜索树,再进行删除时分为三种情况
cur.left == null;
1.cur == root , root == cur.right;
2.cur != root,cur ==pre.left, pre.left =cur.right;
3.cur != root,cur == pre.right, pre.rigth = cur.right;
cur.right == null;
- cur ==root, root ==cur.left;
2.cur !=root,cur =pre.left; pre.left == cur.left;- cur !=root,cur =pre.right , pre.right = cur.left
cur.left !=null && cur.right !=null
可以找左子树的最大值或者右子树的最小值,博主在此选择后者
//删除节点
public void remove(int val) {
if (root == null) return;
BSTNode cur = root;
BSTNode pre = null;
while (cur != null) {
if (cur.val == val) {
remove(cur, pre, val);
return;
} else if (cur.val > val) {
pre = cur;
cur = cur.left;
} else {
pre = cur;
cur = cur.right;
}
}
}
private void remove(BSTNode cur, BSTNode pre, int val) {
if (cur.left == null) {
if (cur == root) {
root = cur.right;
} else if (cur == pre.left) {
pre.left = cur.right;
} else {
pre.right = cur.right;
}
} else if (cur.right == null) {
if (cur == root) {
root = cur.left;
} else if (cur == pre.left) {
pre.left = cur.left;
} else {
pre.right = cur.left;
}
} else {
BSTNode target = cur.right;
BSTNode targetParent = cur;
while (target.left != null) {
targetParent = target;
target = target.left;
}
//target指向右边的最小值
cur.val = target.val;
//对应上图两种状态
if (target == targetParent.left) {
targetParent.left = target.right;
} else {
targetParent.right = target.right;
}
}
}