数据结构--树
Posted 菜鸟_Admin
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了数据结构--树相关的知识,希望对你有一定的参考价值。
无论是链表,栈还是队列,它们都是线性结构的,每个节点的左边最多一个节点,右边也最多一个节点,对于大量的输入数据,线性表的访问时间太慢,不宜使用。这里我要说一种非线性的数据结构,其大部分操作的运行时间平均为O(logn)。
我们涉及到的这种数据结构叫做树。在计算机科学中,树是非常有用的抽象概念。我们形象的去描述一棵树,一个家族的老祖可能有两个儿子,这两个儿子一个有一个儿子,一个有三个儿子,像这样发展下去的一个族谱,就是一个树。下面是常见的一种树:二叉树。
本文中以二叉树为例,将二叉树的数据结构定义,深度计算,几种遍历方式进行JAVA编码实现。
1.二叉树的数据结构
public class BinaryTreeNode { private int data; private BinaryTreeNode leftNode; private BinaryTreeNode rightNode; }
2.深度计算,二叉树的深度计算通过其本身的结构特性可进行递归。
public static int getDepth(BinaryTreeNode treeNode) { if (treeNode == null) { return 0; } int data=treeNode.getData(); System.out.println(data); int left = getDepth(treeNode.getLeftNode()); int right = getDepth(treeNode.getRightNode()); int depth = Math.max(left, right) + 1; return depth; }
3.二叉树的遍历:前,中,后续。广度优先。
/** * 广度优先遍历 * @param treeNode */ public static void visitBreadth(BinaryTreeNode treeNode) { Deque<BinaryTreeNode> queueList =new ArrayDeque<BinaryTreeNode>(); queueList.add(treeNode); while (queueList.size()!=0) { BinaryTreeNode currNode=queueList.peekFirst(); System.out.println(currNode.getData()); if (currNode.getLeftNode()!=null) { queueList.add(currNode.getLeftNode()); } if (currNode.getRightNode()!=null) { queueList.add(currNode.getRightNode()); } queueList.removeFirst(); } } //前序遍历 public void preOrder(BinaryTreeNode subTree){ if(subTree!=null){ System.out.println(subTree.getData()); postOrder(subTree.getLeftNode()); postOrder(subTree.getRightNode()); } } //中序遍历 public void inOrder(BinaryTreeNode subTree){ if(subTree!=null){ postOrder(subTree.getLeftNode()); System.out.println(subTree.getData()); postOrder(subTree.getRightNode()); } } //后续遍历 public void postOrder(BinaryTreeNode subTree) { if (subTree != null) { postOrder(subTree.getLeftNode()); postOrder(subTree.getRightNode()); System.out.println(subTree.getData()); } }
4.测试
public static void main(String[] args) { BinaryTreeNode rootNode=new BinaryTreeNode(1); rootNode.setLeftNode(new BinaryTreeNode(2)); rootNode.setRightNode(new BinaryTreeNode(3)); rootNode.getRightNode().setRightNode(new BinaryTreeNode(5)); rootNode.getRightNode().setLeftNode(new BinaryTreeNode(4)); rootNode.getRightNode().getLeftNode().setLeftNode(new BinaryTreeNode(6)); rootNode.getRightNode().getLeftNode().setRightNode(new BinaryTreeNode(7)); /*int depth=getDepth(rootNode); System.out.println(depth);*/ visitBreadth(rootNode); }
广度优先遍历结果:1 2 3 4 5 6 7
5.关于广度优先遍历
广度优先遍历各个节点,需要使用到队列(Queue)这种数据结构,queue的特点是先进先出,其实也可以使用双端队列,区别就是双端队列首位都可以插入和弹出节点。整个遍历过程如下:
首先将A节点插入队列中,queue(A);
将A节点弹出,同时将A的子节点B,C插入队列中,此时B在队列首,C在队列尾部,queue(B,C);
将B节点弹出,同时将B的子节点D,E插入队列中,此时C在队列首,E在队列尾部,queue(C,D,E);
将C节点弹出,同时将C的子节点F,G,H插入队列中,此时D在队列首,H在队列尾部,queue(D,E,F,G,H);
将D节点弹出,D没有子节点,此时E在队列首,H在队列尾部,queue(E,F,G,H);
直到遍历完成。需要借助一个双向队列作为辅助空间存在。
以上是关于数据结构--树的主要内容,如果未能解决你的问题,请参考以下文章
LeetCode810. 黑板异或游戏/455. 分发饼干/剑指Offer 53 - I. 在排序数组中查找数字 I/53 - II. 0~n-1中缺失的数字/54. 二叉搜索树的第k大节点(代码片段