数据结构-Java实现-树
2015-12-23 09:40
351 查看
二叉查找树
AVL树
树的遍历
…(待续)
AVL树
树的遍历
…(待续)
1、二叉查找树
使二叉树成为二叉查找树的性质是,对于树中的每个节点X,它的左子树中所有项的值小于X的值,而它的右子树中所有项的值大于X的值。//二叉查找树 public class BinarySearchTree<Anytype extends Comparable<? super AnyType>> { //节点类 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;} //contains方法(递归实现) private boolean contains(AnyType x,BinaryNode<AnyType> t) { //节点为空,则该节点为叶子节点,走到头了没找到返回false if(t==null) return false; int compareResult = x.compareTo(t.element); if(compareResult<0) return contains(x,t.left); //比该节点小,则在该节点左子树中继续查找 else if(compareResult>0) return contains(x,t.right); //比该节点大,则在该节点右子树中继续查找 else return true; //不大不小,是它就是它! } //findMin方法(递归实现) private BinaryNode<AnyType> findMin(BinaryNode<AnyType> t) { if(t==null) return null; eles if(t.left==null) return t; return findMin(t.left); } //findMax方法(非递归实现,类似指针) private BinaryNode<AnyType> findMax(BinaryNode<AnyType> t) { if(t!=null) while(t.right!=null) t=t.right; return t; } //insert方法 private BinaryNode<AnyType> insert(AnyType x, BinaryNode<AnyType> t) { if(t==null) return new BinaryNode<AnyType>(x,null,null); int compareResult=x.compareTo(t.element); //插入操作,关键在于t.left和t.right的重置就相当于重新连接 if(compareResult<0) t.left=insert(x,t.left); else if(compareResult>0) t.right=insert(x,t.right); else ; //重复元素不管它 return t; //t在插入后被改变 } //remove方法 private BinaryNode<AnyType> remove(AnyType x, BinaryNode<AnyType> t) { if(t==null) return t; 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(t.left!=null&&t.right!=null) { t.element=findMin(t.right).element; //将右子树的最小数据替换它 t.right=remove(t.element,t.right); //然后迭代地删除那个最小数据 } else t=(t.left !=null)?t.left:t.right; //最后是只有一个儿子节点的情况,将唯一的儿子节点直接替换被删除的节点就好啦 return t; } }
2、AVL树
一颗AVL树是其每个节点的左子树和右子树的高度最多差1的二叉查找树(空树高度定义为-1)。//AVL树 //节点类 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 int height(AvlNode<AnyType> t) { return t==null?-1:t.height; } private AvlNode<AnyType> insert(AnyType x, AvlNode<AnyType> t) { if(t==null) return new AvlNode<AnyType>(x, null, null); int compareResult=compare(x,t.element); //compare方法可以在主类中通过创建Comparator对象定义 if(compareResult<0) //当被插入值小于节点值 { t.left=insert(x,t.left); //则递归地在该节点的左子树中执行插入操作 if(height(t.left)-height(r.right)==2) //==2表示不平衡了 if(compare(x,t.left.element)<0) //x比节点左子节点值小,说明是左左,执行单旋转 t=rotateWhithLeftChild(t); else //否则就是左右,执行双旋转 t=doubleWithLeftChild(t); } else if(compareResult>0) //当被插入值大于节点值 { t.right=insert(x,t.right); //则递归地在该节点的右子树中执行插入操作 if(height(t.right)-height(t.left)==2) //==2表示不平衡 if(compare(x,t.right.element)>0) //x比节点右子节点值大,说明是右右,执行单旋转 t=rotateWhithRightChild(t); else t=doubleWithRightChild(t); } else ; //重复值不予处理 t.height=Math.max(height(t.left),height(t.right))+1; //递归地计算节点的高度 return t; } //左左单旋转 private AvlNode<AnyType> rotateWhithLeftChild(AvlNode<AnyType> k2) { AvlNode<AnyType> k1=k2.left; //k2左子节点 k2.left=k1.right; //由于k2成为k1的右子节点,k1的原本的右子节点断开成为k2的左子节点 k1.right=k2; //k1上提,k2成为k1的右子节点 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> doubleWithLeftChild(AvlNode<AnyType> k3) { k3.left=rotateWhithRightChild(k3.left); //先将第二个节点右右 return rotateWhithLeftChild(k3); //再将第一个节点左左 } //右右单旋转和右左双旋转对称
3、树的遍历
//中序遍历 //重载和递归 public printTree() { if(isEmpty()) System.out.println("Empty tree"); else printTree(root); } private void printTree(BinaryNode<AnyType> t) { if(t!=null) { printTree(t.left); System.out.println(t.element); printTree(t.right); } } //后续遍历 //可计算树的高度 private int height(Binary<AnyType> t) { if(t==null) return -1; else return 1+Math.max(height(t.left),height(t.right)); } //先序遍历 //用深度标记每一个节点的时候可以使用
相关文章推荐
- 数据结构_0: 复杂度分析
- 数据结构 JAVA描述(二) 栈
- 数据结构与算法 LeetCode编程练习--Contains Duplicate II
- 实验1 线性表的顺序实现
- 算法设计题1.20-绪论-第1章-《数据结构习题集》-严蔚敏吴伟民版
- 算法设计题1.19-绪论-第1章-《数据结构习题集》-严蔚敏吴伟民版
- 算法设计题1.17-绪论-第1章-《数据结构习题集》-严蔚敏吴伟民版
- 算法设计题1.16-绪论-第1章-《数据结构习题集》-严蔚敏吴伟民版
- 数据结构实验之排序七:选课名单
- 数据结构 JAVA描述(一) 线性表
- php实现的基本数据结构
- php数据结构算法示例
- 数据结构 线性表JAVA实现
- 绪论-第1章-《数据结构习题集》答案解析-严蔚敏吴伟民版
- 数据结构实验之查找二:平衡二叉树
- 数据结构基础(C语言版)(朱仲涛翻译)代码学习 第一章002
- 【ShancoLove】带你看数据结构——第十五课:哈夫曼树
- 【ShancoLove】带你看数据结构——第十四课:通讯录
- JVM启动过程的重要数据结构
- poj 1308 Is It A Tree? 数据结构 并查集