二叉查找树及Avl树

定义不再叙述,看程序
应该是这本书,我看的第二版
https://book.douban.com/subject/10530466/
下面是二叉查找树,我认为比较好的一点是在插入的时候返回修改的子树,代替了c里面的指针,这是我看c数据结构想改写为java时所没有想到的。
还有一点,用户在插入时是不知道root的,而插入函数需要root,所以要有两个插入函数,一个是外部的,只传入值;一个是内部的,传入值和子树的根。书上直接写成了函数重载。


package copy_from_book;

import java.lang.reflect.UndeclaredThrowableException;

public class BinarySearchTree<AnyType extends Comparable<?super AnyType>> {

//内部类
	//.定义在别的类内部、函数内部的类。
	//.内部类能直接访问外部的全部资源。
	//.外部是函数时,只能访问那个函数里 final的变量。
	private static class BinaryNode<AnyType>
	{
		BinaryNode(AnyType theElement)
		{this(theElement,null,null);}
		
		BinaryNode(AnyType theElement,BinaryNode<AnyType> lt,
				BinaryNode<AnyType> rt)
		{element=theElement;left=lt;right=rt;}
		
		AnyType element;
		BinaryNode<AnyType> left;
		BinaryNode<AnyType> right;
	}
	
	private BinaryNode<AnyType>  root;
	
	public BinarySearchTree()
	{root=null;}
	
	public void makeEmpty()
	{root=null;}
	
	public boolean isEmpty()
	{return root==null;}
	
	//下面很多函数重载,是因为
	//从外部使用函数public,是不知道root
	//而调用这些函数(很多次递归,又要用到子树的root)
	//所以public去调用private的重载函数
	public boolean contains(AnyType x)
	{return contains(x,root);}
	
	public AnyType findMin()
	{
		
		if(isEmpty())  throw new UndeclaredThrowableException(null);
		return findMin(root).element;
	}
	
	public AnyType findMax()
	{
		if(isEmpty())  throw new UndeclaredThrowableException(null);
		return findMax(root).element;
	}
	
	
	public void insert(AnyType x)
	{root=insert(x,root);}
	
	public void remove(AnyType x)
	{root=remove(x,root);}
	
	
	
	
	private boolean contains(AnyType x,BinaryNode<AnyType>t)
	{
		if(t==null)
			return false;
		int compareResult=x.compareTo(t.element);
		//返回x-t.element的符号函数
		if(compareResult<0)
			return contains(x,t.left);
		else if(compareResult>0)
			return contains(x,t.right);
		else
			return true;
	}
	
	
	private BinaryNode<AnyType> findMin(BinaryNode<AnyType>t)
	{
		if(t==null)
			return null;
		else if(t.left==null)
			return t;
		else
			return findMin(t.left);
	}
	
	
	
	private BinaryNode<AnyType> findMax(BinaryNode<AnyType>t)
	{
		if(t!=null) 
		{
			while(t.right!=null)
				t=t.right;	
		}
		
		
		return t;
	}
	
	
	
	
	
	private BinaryNode<AnyType> insert(AnyType x,BinaryNode<AnyType>t)
	{
		//return the new root of the subtree这个方法太好了
		//用了这个就可以避免C里面实现时需要传入指针来改变参数
		
		/* * @param x the item to insert * @param t the node that roots the subtree * @return the new root of the subtree */
		if(t==null)
			return new BinaryNode<AnyType>(x,null,null);
		int compareResult=x.compareTo(t.element);
		//返回x-t.element的符号函数
		if(compareResult<0)
			t.left=insert(x,t.left);
		else if(compareResult>0)
			t.right=insert(x,t.right);
		else
			;//Duplicate; do nothing
		return t;
	}
	
	
	
	
	private BinaryNode<AnyType> remove(AnyType x,BinaryNode<AnyType>t)
	{
		/* *@param x the item to remove *@param t the node that roots the subtree *@return the new root of the subtree */
		
		//如果删除的次数不多,可以采用“懒惰删除”:
		//当一个元素要被删除时,保留元素在树里
		//只是标记为删除。在有重复项时常用。
		if(t==null)
			return t;//not found;do nothing
		
		int compareResult=x.compareTo(t.element);
		
		if(compareResult<0)
			t.left=remove(x,t.left);
		else if(compareResult>0)
			t.right=remove(x,t.right);
		else if(t.left!=null&&t.right!=null)
		{
			//两趟搜索查找和删除,效率不高,
			//可以调整。
			
			
			//替换t的元素为右子树最小元素
			//删除右子树的最小元素
			t.element=findMin(t.right).element;
			t.right=remove(t.element,t.right);
		}
		
		else
			t=(t.left!=null)?t.left:t.right;
		
		return t;
		
		
	}
	
	
	public static void main(String []args)
	{
		int m[]=new int[] {1,25,6,8,5,4,2};
		BinarySearchTree<Integer> b=new BinarySearchTree<Integer>();
		for(int i=0;i<m.length;i++)
		{
			b.insert(m[i]);
		}
		System.out.println();
	}}


AVL树
书上写的不全,我又补充了一些。(原来写错了,我又改正了)

package df;

public class Avl<AnyType extends Comparable<?super AnyType>> {
	
	
	
	
	private static class AvlNode<AnyType> 
	{
		AvlNode(AnyType theElement)
		{this(theElement,null,null);}//调用下面的构造器
		
		
		AvlNode(AnyType theElement,AvlNode<AnyType>lt,
				AvlNode<AnyType>rt)
		{element=theElement;
		left=lt;
		right=rt;}
		
		AnyType element;
		AvlNode<AnyType>  left;
		AvlNode<AnyType>  right;
		int height;
	}
	
	private AvlNode<AnyType> root;
	
	private int height(AvlNode<AnyType> t)
	{
		return t==null?-1:t.height;
	}
	
	
	public void insert(AnyType x)
	{
		root=insert(x,root);
	}
	
	
	private AvlNode<AnyType> insert(AnyType x,AvlNode<AnyType>t)
	{
		/* * @param x the item to insert * @param t the node that roots the subtree * @return the new root of the subtree */
		if(t==null)
			return new AvlNode<AnyType>(x,null,null);
		
		int compareResult=x.compareTo(t.element);
		if(compareResult<0)
		{
			t.left=insert(x,t.left);
			if(height(t.left)-height(t.right)==2)
				if(x.compareTo(t.left.element)<0)
					t=rotateWithLeftChild(t);
				else
					t=doubleWithLeftChild(t);
		}
		else if(compareResult>0)
		{
			t.right=insert(x,t.right);
			if(height(t.right)-height(t.left)==2)
				if(x.compareTo(t.right.element)>0)
					t=rotateWithRightChild(t);
				else
					t=doubleWithRightChild(t);
		}
		
		else;//do nothing
		t.height=Math.max(height(t.left), height(t.right))+1;
		return t;
	}


	private AvlNode<AnyType> rotateWithLeftChild(AvlNode<AnyType>k2)
	{//插在左子树的左边
		AvlNode<AnyType>k1=k2.left;
		k2.left=k1.right;
		k1.right=k2;
		k2.height=Math.max(height(k2.left), height(k2.right))+1;
		k1.height=Math.max(height(k1.left), k2.height)+1;

		return k1;
	}
	
	
	private AvlNode<AnyType> rotateWithRightChild(AvlNode<AnyType>k2)
	{//插在右子树的右边
		AvlNode<AnyType>k1=k2.right;
		k2.right=k1.left;
		k1.left=k2;
		k2.height=Math.max(height(k2.left), height(k2.right))+1;
		k1.height=Math.max(height(k1.right), k2.height)+1;

		return k1;
	}
	

	private AvlNode<AnyType>  doubleWithLeftChild(AvlNode<AnyType> k3)
	{//插在左子树右边
		k3.left=rotateWithRightChild(k3.left);
		return rotateWithLeftChild(k3); 
	}
	
	
	
	private AvlNode<AnyType>  doubleWithRightChild(AvlNode<AnyType> k3)
	{//插在右子树左边
		k3.right=rotateWithLeftChild(k3.right);
		return rotateWithRightChild(k3); 
	}

	public static void main(String args[])
	{
		int a[]=new int[] {3,2,1,4,5,6,7,16,15,14,13,12,11,10,8,9};
		Avl<Integer>avl=new Avl<Integer>();
		for(int i=0;i<a.length;i++)
			avl.insert(a[i]);
		System.out.println();
		System.out.println();
	}

}

    原文作者:AVL树
    原文地址: https://blog.csdn.net/weixin_41677899/article/details/84546476
    本文转自网络文章,转载此文章仅为分享知识,如有侵权,请联系博主进行删除。
点赞