二叉树的基本性质、存储方式与遍历(Python实现)
来源:互联网 发布:执行仪表板软件 编辑:程序博客网 时间:2024/05/24 23:12
二叉树
二叉树(Binary Tree)是树的一种特殊形式,也就是每个节点之下最多拥有2个孩子,相应地若最多不超过M个孩子,那就成为M叉树,但实际上我们统称为多叉树。对于二叉树,常用的定理有四条:
- 深度为i的二叉树最多含有
2i−1 个节点; - 第i层至多有
2i−1 个节点; 对于任意一颗二叉树,若其终端节点数为
n0 ,度为2的节点数为n2 ,则n0=n2+1 。证明如下:(1)n=n0+n1+n2 (2)n=B+1(B为分支总数) (3)B=n1+2n2
由上述三式即可得出此定理。对于一棵完全二叉树(除最后一层外每一层都为满二叉树)而言,其叶子节点数具有以下关系:
n0=n2(当n为偶数时)或n+12(当n为奇数时)
二叉树的存储
在将二叉树的存储之前,我们先了解一下树的存储方式,常用输的存储方式有三种,在介绍之前,我们先把树的例子放出来,再来看各种存储方式的不同。
- 双亲表示法
所谓双亲表示法就是会设置一个指示器来指向其双亲所在的位置。那么我最终应当会存储为一个如下的数组:
- 优点:Parent(T,x)可以很快找到双亲
- 缺点:求节点的孩子时就必须遍历整个结构
- 孩子表示法
所谓孩子表示法就是会在数据后面存储其孩子节点,但也有两种方式:- 方法一:
但是这样的方法比较浪费空间,因为你并不知道多叉树中每个节点一共有多少个孩子节点,而不存在的节点,也必须进行保存为null; - 方法二:
这样的方法相对于第一种加入了degree的值,可以更节省空间,但是对树进行插入或删除等的操作的时候却增加了复杂度。
- 方法一:
- 孩子兄弟表示法
孩子兄弟表示法也是二叉树的一种表示方法,数据的两端分别存放其左节点的孩子和其兄弟节点。
其数据结构也可以很方便的定义:
typedef struct CSNode{ElementType data;Struct CSNode *firstchild,*nextsibling;} CSNode,*CSTree;
二叉树的遍历
所谓遍历(Traversal)是指沿着某条搜索路线,依次对树中每个结点均做一次且仅做一次访问。访问结点所做的操作依赖于具体的应用问题。
遍历是二叉树上最重要的运算之一,是二叉树上进行其它运算之基础。
从二叉树的递归定义可知,一棵非空的二叉树由根结点及左、右子树这三个基本部分组成。因此,在任一给定结点上,可以按某种次序执行三个操作:
(1)访问结点本身(N),
(2)遍历该结点的左子树(L),
(3)遍历该结点的右子树(R)。
在访问时要求必须先访问左子树再访问右子树,按照对根节点的访问顺序,二叉树的遍历分为三种:先序中序和后序遍历。
我们还是以刚才的二叉树作为例子,那么
- 先序遍历的结果应该为:RACDBEF
- 中序遍历的结果应该为:CADREBF
- 后序遍历的结果应该为:CDAEFBR
用二叉链表做为存储结构,中序遍历算法可描述为:
void InOrder(BinTree T) { if(T) { // 如果二叉树非空 InOrder(T->lchild); printf("%c",T->data); // 访问结点 InOrder(T->rchild); } } // InOrder
代码实现
#! /usr/bin/env python # -*-coding:utf-8 -*- # Fuction: Create a binary search tree and tranversal in different way # Coder: Memory # Date: 2015-04-18 class treeNode(): def __init__(self, data, left, right): self.data = data self.left = left self.right = right class BTree: def __init__(self): self.root = None def is_empty(self): if self.root is None: return True else: return False def insert(self, data): r = self.root if r is None: self.root = treeNode(data, None, None) return while True: # 比根结点小放在左边 if r.data > data: if r.left is None: r.left = treeNode(data, None, None) break else: r = r.left else: # 比根结点大放在右边 if r.right is None: r.right = treeNode(data, None, None) break else: r = r.right def traversal(self, root): if root is None: return else: # 先序遍历 print root.data self.traversal(root.left) # 中序遍历去掉下一行的注释 # print root.data self.traversal(root.right) # 后序遍历同上 # print root.dataif __name__ == '__main__': bt = BTree() bt.insert(10) bt.insert(3) bt.insert(12) bt.insert(6) bt.insert(24) bt.insert(30) bt.insert(1) bt.insert(5) # 若用户输入的是数组,就一个个一个地输入就好了。 bt.traversal(bt.root)
二叉树的应用和衍生有很多,比如:哈夫曼树(最优二叉树),二叉搜索树等等。将在后续的博文中一一介绍。
- 二叉树的基本性质、存储方式与遍历(Python实现)
- 二叉树 二叉树的性质 存储结构 遍历二叉树 C实现二叉树的创建和遍历 线索二叉树
- 二叉树 二叉树的性质 存储结构 遍历二叉树 C实现二叉树的创建和遍历 线索二叉树
- 二叉树与遍历的Python实现
- 二叉搜索树的性质与实现
- 二叉树的基本性质
- 二叉树的基本性质
- 二叉树的基本性质
- 二叉树的基本性质
- 二叉树的基本性质及使用实现
- 二叉树的概念,二叉树的数据存储结构,二叉树的性质,二叉树的遍历方法数据结构-树的学习(3)
- 树与二叉树基本性质相关
- 二叉搜索树的基本概念、性质及Python实现
- 二叉树的定义、性质、存储
- 二叉树的定义、性质、存储
- 二叉树的定义、性质、存储
- 二叉树的定义、性质、存储
- 二叉树的定义、性质、存储
- 关于如何删除VC++工程中的类的.cpp和.h文件
- 最小生成树Kruskal算法实现+快排实现权值排序
- 【云分析】之七《80%的企业正在或考虑使用行业云》
- C# StreamReader类 basestream.seek(0,seekorigin.begin)
- POJ 2479 Maximum sum ( DP )
- 二叉树的基本性质、存储方式与遍历(Python实现)
- github之Feature分支
- PAT--Saving James Bond - Hard Version
- Unity 3D
- HDU 4687 Boke and Tsukkomi (一般图匹配带花树)
- 分布式消息系统—kafka入门
- linux 动态链接库
- POJ 3041 - Asteroids(二分图匹配)
- Sizeof