在上一篇博客中(Java之二叉树的手动构建与遍历)我们了解了二叉树的基本知识,知道二叉树可以用来存储数据,并且有多种遍历方式,那么我们联想到如果我们有一组数据需要排序,能否利用二叉树实现呢?
答案是当然可以!下面就来一步步实现!
一,节点属性规定
节点根据连接关系有四个属性:
1,父节点
2,左子节点
3,右子节点
4,节点值
class Node{
Node paren;
Node left;
Node right;
int value;
//构造方法 实例化节点时要传参
public Node(int value) {
this.value=value;
}
}
二,添加数据方法
在这里我们规定将小于根节点值的数据放入左子树,大于根节点值的数据数据放入右子树。
添加方法如下:
1,若根节点为空则先创建根节点(根节点只在第一次调用该方法时创建一次)。
当根节点创建完毕后每次添加数据时:
2,每添加一个数据都从根节点开始判断,将当前节点指向根节点。
3,如果需要添加的数据小于当前节点的值,往左子树查找,如果左子节点为空,将该值放入左子节点中;如果左子节点不为空,当前节点指向该左子节点。
4,如果需要添加的数据大于当前节点的值,往右子树查找,如果右子节点为空,将该值放入右子节点中;如果右子节点不为空,当前节点指向该右子节点。
重复执行3、4步,直到将数据存入节点中,添加一个数据的步骤完成。
Node root=null;//初始化根节点 只声明 并没有实例化
//创建节点 建立连接
public void creteNode(int value) {
//每次都从根节点开始
Node currNode=root;//将当前节点指向根节点 根节点为固定已申明的节点
//没有根节点先创建根节点 只创建一次
if(currNode==null) {
root = new Node(value);//当根节点被实例化一次后该if条件就不满足 跳到执行while循环
return;
}
while(true) { //可以按照值的大小无论哪个位置都能正确安放 不断查找 直到找到合适位置创建节点
//左小右大
if(value<currNode.value) {
if(currNode.left==null) {
currNode.left=new Node(value);
return;
}else {
currNode = currNode.left;//又执行while循环从当前重新给定的node节点进行值判断
}
}
else {
if(currNode.right==null) {
currNode.right=new Node(value);
return;
}else {
currNode=currNode.right;//又执行while循环从当前重新给定的node节点进行值判断
}
}
}
}
三,中序遍历
在构建好树后,我们选择中序遍历该树,因为中序遍历的顺序是:左子->父->右子。在上述构建的方法中,我们将小于根节点的值放在了左子树,大于根节点的值放在了右子树,利用中序遍历就能将节点的数据从小->大依次取出了。
//中序遍历 传入根节点找到此棵树 递归调用
public void midOrder(Node n) {
//当所有节点访问完后就退出递归
if(n==null) {
return;
}
midOrder(n.left);//1,先访问左子节点
System.out.println(n.value);//2,再访问父节点
midOrder(n.right);//最后访问右子节点
}
public static void main(String[] args) {
ordertree tree = new ordertree();
int[] array= {60,23,1,66,50,43,100};
for(int i=0;i<array.length;i++) {//创建树
tree.creteNode(array[i]);
}
tree.midOrder(tree.root);//树已经建立好 根节点已被实例化 将根节点传入 中序遍历该树
}
构建的树如下:
中序遍历结果:
完整代码:
百度网盘提取码:5ze2