平衡二叉树的插入查找删除
Posted 鸟随二月
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了平衡二叉树的插入查找删除相关的知识,希望对你有一定的参考价值。
二叉平衡树的节点
package main.AVL;
public class AVLNode {
private int value;
private int bf;
private AVLNode left;
private AVLNode right;
private AVLNode parent;
public int getValue() {
return value;
}
public void setValue(int value) {
this.value = value;
}
public int getBf() {
return bf;
}
public void setBf(int bf) {
this.bf = bf;
}
public AVLNode getLeft() {
return left;
}
public void setLeft(AVLNode left) {
this.left = left;
}
public AVLNode getRight() {
return right;
}
public void setRight(AVLNode right) {
this.right = right;
}
public AVLNode getParent() {
return parent;
}
public void setParent(AVLNode parent) {
this.parent = parent;
}
public AVLNode(int value, int bf, AVLNode left, AVLNode right, AVLNode parent) {
this.value = value;
this.bf = bf;
this.left = left;
this.right = right;
this.parent = parent;
}
@Override
public String toString() {
return "AVLNode{" +
"value=" + value +
", bf=" + bf +
'}';
}
}
小结
本人参考插入作品想继续写下删除的操作,又参考了该视频准备进行相应的编码,但在落笔前怎么也感觉删除操作与插入操作不同,感觉处理好子树的平衡后,父树不一定平衡,又参考了该作品,知道了失衡会传播,所以即使小编将子树失衡平衡好以后,还要进行父树平衡,进行节点中的平衡因子bf属性的修改,所以这里删除编码时小编偷了一个懒,,删除特定节点时,对平衡二叉树进行了重建。
代码
package main.AVL;
public class AVLTree {
private AVLNode root;
//右旋,针对失衡LL型
public void rightRotate(AVLNode t){
AVLNode left=t.getLeft();
AVLNode parent=t.getParent();
t.setLeft(left.getRight());
if(left.getRight()!=null){
left.getRight().setParent(t);
}
left.setRight(t);
left.setParent(parent);
t.setParent(left);
if(parent==null){
root=left;
}else if (parent.getLeft()==t){
parent.setLeft(left);
}else{
parent.setRight(left);}
t.setBf(0);
left.setBf(0);
}
//左旋RR型失衡
public void leftRotate(AVLNode t){
AVLNode right=t.getRight();
AVLNode parent=t.getParent();
t.setRight(right.getLeft());
if (right.getLeft()!=null){
right.getLeft().setParent(t);
}
right.setLeft(t);
t.setParent(right);
right.setParent(parent);
if(parent==null){
root=right;
}else if(parent.getLeft()==t){
parent.setLeft(right);
}else{
parent.setRight(right);
}
t.setBf(0);
right.setBf(0);
}
//左右旋针对LR旋
public void leftRightRotate(AVLNode t){
AVLNode parent=t.getParent();
AVLNode left=t.getLeft();
AVLNode leftRight=left.getRight();
left.setRight(leftRight.getLeft());
if (leftRight.getLeft()!=null){
leftRight.getLeft().setParent(left);
}
t.setLeft(leftRight.getRight());
if (leftRight.getRight()!=null){
leftRight.getRight().setParent(t);
}
leftRight.setLeft(left);
left.setParent(leftRight);
leftRight.setRight(t);
t.setParent(leftRight);
leftRight.setParent(parent);
if (parent==null){
root=leftRight;
}else if(parent.getLeft()==t){
parent.setLeft(leftRight);
}else{
parent.setRight(leftRight);
}
if (leftRight.getBf()==1){
t.setBf(-1);
left.setBf(0);
leftRight.setBf(0);
}else if (leftRight.getBf()==-1){
t.setBf(0);
left.setBf(1);
leftRight.setBf(0);
}else{
t.setBf(0);
left.setBf(0);
}
}
//右左旋针对的是RL型失衡
public void rightLfetRotate(AVLNode t){
AVLNode parent=t.getParent();
AVLNode right=t.getRight();
AVLNode rightLeft= right.getLeft();
right.setLeft(rightLeft.getRight());
if (rightLeft.getRight()!=null){
rightLeft.getRight().setParent(right);
}
t.setRight(rightLeft.getLeft());
if (rightLeft.getLeft()!=null){
rightLeft.getLeft().setRight(t);
}
rightLeft.setLeft(t);
t.setParent(rightLeft);
rightLeft.setRight(right);
right.setParent(rightLeft);
rightLeft.setParent(parent);
if (parent==null){
root=rightLeft;
}else if (parent.getLeft()==t){
parent.setLeft(rightLeft);
}else{
parent.setRight(rightLeft);
}
if (rightLeft.getBf()==1){
t.setBf(0);
right.setBf(-1);
rightLeft.setBf(0);
}else if (rightLeft.getBf()==-1){
t.setBf(1);
right.setBf(0);
rightLeft.setBf(0);
}else{
t.setBf(0);
right.setBf(0);
}
}
//插入节点
public String insert(int i){
AVLNode key=new AVLNode(i,0,null,null,null);
//1.插入前是空树插入节点
if (root==null){
root=key;
return "Success";
}
//2.插入前不是空树
// 找位置
AVLNode pre=null;
AVLNode current=root;
while(current!=null){
pre=current;
if (current.getValue()>i){
current=current.getLeft();
}else if (current.getValue()<i){
current=current.getRight();
}else
return "Success";
}
//插入
key.setParent(pre);
if (pre.getValue()<i)
pre.setRight(key);
else
pre.setLeft(key);
//修改平衡因子并寻找最近的失衡节点
current=key;
while(pre!=null){
if (pre.getLeft()==current){
pre.setBf(pre.getBf()+1);
}else{
pre.setBf(pre.getBf()-1);
}
if (Math.abs(pre.getBf())>=2)
break;
current=pre;
pre=pre.getParent();
}
if (pre==null)
return "Success";
if (pre.getBf()==2&¤t.getBf()==1)
this.rightRotate(pre);
else if (pre.getBf()==2&¤t.getBf()==-1)
this.leftRightRotate(pre);
else if(pre.getBf()==-2&¤t.getBf()==1)
this.rightLfetRotate(pre);
else if (pre.getBf()==-2&¤t.getBf()==-1)
this.leftRotate(pre);
return "Success";
}
//前序输入平衡二叉树;
public void print(){
this.print(root);
}
public void print( AVLNode current){
if (current.getLeft()!=null){
this.print(current.getLeft());
}
System.out.println(current);
if (current.getRight()!=null){
this.print(current.getRight());
}
}
//查找某一点
public AVLNode select(int k){
return this.select(this.root,k);
}
public AVLNode select(AVLNode root,int k){
AVLNode temp=null;
if (root!=null){
if (root.getValue()==k)
temp=root;
if (temp==null)
temp=this.select(root.getLeft(),k);
if (temp==null)
temp=this.select(root.getRight(),k);
}
return temp;
}
//求树的高度
public int height(AVLNode root){
if (root==null)
return 0;
return Math.max(this.height(root.getLeft()),this.height(root.getRight()))+1;
}
//删除节点
public String delete(int k){
AVLNode current=this.select(k);
//删除节点
if (current==null)
return "Success";
if (current==this.root){
this.root=null;
return "Success";
}
AVLTree two=new AVLTree();
this.againBuild(this.root,two,k);
this.root=two.root;
return "Success";
}
public void againBuild(AVLNode root,AVLTree two,int k){
if (root!=null){
againBuild(root.getLeft(),two,k);
if (root.getValue()!=k)
two.insert(root平衡二叉树的操作(高手进)