二叉搜索树会有可能出现极左/右的情况,平衡二叉树,在该基础上增加了深度判断,如果左右两边的子树深度差==2的情况下,旋转失去平衡的二叉树。使整课树都是平衡的状态,时间的复杂度为o(logn)。
旋转的四种情况
旋转情况1

旋转情况2

旋转情况3

旋转情况4

代码实现
TreeNode
public class BalanceTreeNode {
public int value;
public BalanceTreeNode right;
public BalanceTreeNode left;
public int height = 1; // 处理平衡的高度
public BalanceTreeNode(int value) {
this.value = value;
}
}
private BalanceTreeNode root;
public void put(int value) {
root = add(root, value);
}
public void remove(int value) {
root = remove(root, value);
}
//和添加处理一直,但是左右相反。
private BalanceTreeNode remove(BalanceTreeNode node, int value) {
if (node == null) {
return null;
}
if (value > node.value) {
node.right = remove(node.right, value);
int leftHeight = getHeight(node.left);
int rightHeight = getHeight(node.right);
//删除右边的节点,那么左边的节点大于右边的节点,失去平衡的情况下,进行旋转
if (leftHeight - rightHeight == 2) {
// 如果出现“情况3”的情况,先对左孩子进行左旋,在右旋
if (getHeight(node.left.right) > getHeight(node.left.left)) {
node = L_R_Ration(node);
} else {
node = L_Rotation(node);
}
}
} else if (value < node.value) {
node.left = remove(node.left, value);
int leftHeight = getHeight(node.left);
int rightHeight = getHeight(node.right);
if (rightHeight - leftHeight == 2) {
if (getHeight(node.right.left) > getHeight(node.right.right)) {
node = R_L_Ration(node);
} else {
node = R_Rotation(node);
}
}
} else {
if (node.right == null && node.left == null) {
node = null;
return null;
} else if (node.right == null && node.left != null) {
BalanceTreeNode left = node.left;
node = null;
return left;
} else if (node.right != null && node.left == null) {
BalanceTreeNode right = node.right;
node = null;
return right;
} else {
// 在左边查找最大的节点
BalanceTreeNode maxNode = maxNode(node.left);
maxNode.left = delMaxNode(node.left);
maxNode.right = node.right;
node = null;
return maxNode;
}
}
node.height = Math.max(getHeight(node.left), getHeight(node.right)) + 1;
return node;
}
private BalanceTreeNode delMaxNode(BalanceTreeNode node) {
if (node != null) {
BalanceTreeNode leftNode = node.left;
node = null;
return leftNode;
}
node = delMaxNode(node.right);
return node;
}
private BalanceTreeNode maxNode(BalanceTreeNode node) {
if (node.right == null) {
return node;
}
return maxNode(node.right);
}
private BalanceTreeNode add(BalanceTreeNode node, int value) {
if (node == null) {
BalanceTreeNode newNode = new BalanceTreeNode(value);
return newNode;
}
// 放在节点的右边
if (value > node.value) {
node.right = add(node.right, value);
int leftHeight = getHeight(node.left);
int rightHeight = getHeight(node.right);
// 当右子树的高度大于左子树的高度
if (rightHeight - leftHeight == 2) {
//如果出现“情况4”的状况,先对右孩子进行右旋
if (getHeight(node.right.left) > getHeight(node.right.right)) {
node = R_L_Ration(node);
} else {
// 否则进行左旋
node = L_Rotation(node);
}
}
} else if (value < node.value) { // 放在节点的左边
node.left = add(node.left, value);
int leftHeight = getHeight(node.left);
int rightHeight = getHeight(node.right);
// 当左边的高度大于右边的高度 进行旋转
if (leftHeight - rightHeight == 2) {
// 如果出现“情况3”的情况,先对左孩子进行左旋,在右旋
if (getHeight(node.left.right) > getHeight(node.left.left)) {
node = L_R_Ration(node);
} else {
// 否则直接进行右旋
node = R_Rotation(node);
}
}
} else {
node.value = value;
}
node.height = Math.max(getHeight(node.left), getHeight(node.right)) + 1;
return node;
}
private BalanceTreeNode L_R_Ration(BalanceTreeNode node) {
node.left = L_Rotation(node.left);
return R_Rotation(node);
}
private BalanceTreeNode R_L_Ration(BalanceTreeNode node) {
//右旋
node.right = R_Rotation(node.right);
//在左旋
return L_Rotation(node);
}
private BalanceTreeNode R_Rotation(BalanceTreeNode node) {
BalanceTreeNode left = node.left;
BalanceTreeNode rigth = left.right;
left.right = node;
node.left = rigth;
node.height = Math.max(getHeight(node.left), getHeight(node.right));
left.height = Math.max(getHeight(left.left), getHeight(left.right));
return left;
}
private BalanceTreeNode L_Rotation(BalanceTreeNode node) {
BalanceTreeNode right = node.right;
BalanceTreeNode left = right.left;
right.left = node;
node.right = left;
node.height = Math.max(getHeight(node.left), getHeight(node.right)) + 1;
right.height = Math.max(getHeight(right.left), getHeight(right.right)) + 1;
return right;
}
private int getHeight(BalanceTreeNode node) {
return node == null ? 0 : node.height;
}
public void print() {
LinkedList<BalanceTreeNode> linkedList = new LinkedList<>();
if (root != null) {
linkedList.push(root);
}
while (!linkedList.isEmpty()) {
BalanceTreeNode BalanceTreeNode = linkedList.pop();
System.out.print(BalanceTreeNode.value);
if (BalanceTreeNode.left != null) {
linkedList.add(BalanceTreeNode.left);
}
if (BalanceTreeNode.right != null) {
linkedList.add(BalanceTreeNode.right);
}
}
}
public static void main(String[] args) {
SearchBalanceTree tree = new SearchBalanceTree();
tree.put(3);
tree.put(2);
tree.put(5);
tree.put(4);
tree.remove(2);
tree.print();
}
}