二叉树种类 二叉树种类定义没有一个标准化,所以不同文档可能有不同解释。
rooted binary tree
full binary tree
complete binary tree
除去最后一级,其他级都是full状态(0个或者2个子节点),且最后一级的节点都在左侧子树上。
perfect binary tree
infinite complete binary tree
every node has two children (and so the set of levels is countably infinite). The set of all nodes is countably infinite, but the set of all infinite paths from the root is uncountable, having the cardinality of the continuum
我的理解就是无穷尽的rooted binray tree
balanced binary tree
左右子树高度差不超过1
且左右子树各自均为平衡二叉树
degenerate tree
遍历方式 前序遍历(深度优先)
* 指先访问根,然后访问子树的遍历方式。
* 顺序 `F, B, A, D, C, E, G, I, H.`
堆栈代码实现:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 class BinTree(object): def __init__(self,root): self.root = root self.left = None self.right = None def preorder(self, root): if root is None: return stack = [] node = root while node or stack: while node: print (node.root) stack.append(node) node = node.left node = stack.pop() node = node.right root = BinTree('F' ) root.left = BinTree('B' ) root.right = BinTree('G' ) root.left .left = BinTree('A' ) root.left .right = BinTree('D' ) root.left .right .left = BinTree('C' ) root.left .right .right = BinTree('E' ) root.right .right = BinTree('I' ) root.right .right .left = BinTree('H' ) root.preorder(root)
解释: 从最顶层的根进入,然后打印出这个根,并且压入栈,然后获取这个根的左节点,依次循环,直到左节点无法获取到,然后出栈,这边出栈出来的为最后压入的根 (也就是底层的左节点),然后开始遍历其右边的子树,右边子树也是从左边开始,也是压入栈,依次循环。
中序遍历(深度优先)
* 指先访问左(右)子树,然后访问根,最后访问右(左)子树的遍历方式。
* 顺序 `A, B, C, D, E, F, G, H, I.`
堆栈代码实现:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 class BinTree(object): def __init__(self,root): self.root = root self.left = None self.right = None def midorder(self,root): if root is None: return stack = [] node = root while node or stack: while node : # 根压入栈 stack .append(node ) # 赋予左节点 node = node.left node = stack .pop() print(node.root) node = node .right
解释:因为是左右中的方式,所以root是最迟打印的,则先把左边的都依次压栈,然后压入最后一个,开始逐步弹出,弹出就打印一个,然后遍历弹出的右子树,也是一样的方法,依次循环,直到全部退出,打印出最顶层的root。
后序遍历(深度优先)
* 指先访问子树,然后访问根的遍历方式。子树先左后右在根节点。
* 顺序 `A, C, E, D, B, H, I, G, F.`
堆栈代码实现:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 class BinTree (object ): def __init__ (self,root ): self.root = root self.left = None self.right = None def backorder (self, root ): if root is None : return mystack1 = [] mystack2 = [] node = root mystack1.append(node) while mystack1: node = mystack1.pop() if node.left: mystack1.append(node.left) if node.right: mystack1.append(node.right) mystack2.append(node) while mystack2: print(mystack2.pop().root)
解释:因为顺序为从最左节点 开始,且需要判断是否存在根的左右子节点,且不是连续,所以需要用到两个栈。mystack1放入的是当前遍历的节点,然后往mystack2中压入,这个行为之前还对节点进行左右判断,先往stack1中压入左边的节点,然后压入右边的节点,轮到下次循环的时候,后放入stack1中的(右子树)被先pop出来,然后被插入到stack2中,此时stack2中存放的顺序,根节点,然后右节点,接着左节点,依次循环,直到把stack2给压满。最后一个while执行的时候,按照左右根的顺序打印出来,就实现了。
层级遍历(广度优先)
* 广度优先遍历会先访问离根节点最近的节点。二叉树的广度优先遍历又称按层次遍历。算法借助队列实现。
* 顺序 `F, B, G, A, D, I, C, E, H.`
队列代码实现:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 class BinTree (object ): def __init__ (self,root ): self.root = root self.left = None self.right = None def levelorder (self, root ): if root is None : return myqueue = [] node = root myqueue.append(node) while myqueue: node = myqueue.pop(0 ) print(node.root) if node.left: myqueue.append(node.left) if node.right: myqueue.append(node.right)
解释:通过队列方式实现,比较简单,抓到元素append进去,一左一右方式放入,弹出的时候弹出第一个元素,并且打印。
refer
https://www.geeksforgeeks.org/binary-tree-set-3-types-of-binary-tree/ https://en.wikipedia.org/wiki/Binary_tree#Types_of_binary_trees https://blog.yangx.site/2016/07/22/Python-binary-tree-traverse/ https://zh.wikipedia.org/zh-hant/%E6%A0%91%E7%9A%84%E9%81%8D%E5%8E%86