数据结构(六)——树和二叉树
一、树和二叉树的定义与存储
1.树的定义
树是一种非线性的数据结构,它是由n个有限结点组成有层次关系的集合
树具有以下特点:
(1)每个结点具有0个或多个子结点
(2)每个子结点只有一个父结点
(3)没有前驱的结点为根结点
(4)除了根结点外,每个子结点又可以由m棵不相关的子树组成
2.树的基本术语
(1)结点的度:结点拥有的子树数量称为结点的度
(2)树的度:树内各结点度的最大值,即上图 D结点的度就是此树的度
(3)叶子:度为 0的节点称为叶子或终端节点
(4)结点的层次和树的深度
结点的从根开始定义起,根为第一层,根的孩子为第二层,以此类推,树的深度或高度是树中结点的最大层次
(5)森林:m棵互不相交的树的集合
3.二叉树与树主要有以下区别:
(1)二叉树每个结点至多只有两颗子树(即二叉树中不能存在度大于2的结点)
(2)二叉树的子树有左右之分,其次序不能任意颠倒
(3)即使树中某结点只有一颗子树,也要区分它是左子树还是右子树
4.二叉树的性质:
性质1:在二叉树的第i层上至多有 2的i-1次方 个结点(i>=1)
性质2:深度为k的二叉树至多有 2的k次方-1 个结点(k>=1)
性质3:对任何一棵二叉树T,如果其终端结点数为n0,度为2的结点数为n2,则n0=n2+1
【证明】一棵二叉树,除了终端结点(叶子结点),就是度为1或2的结点。假设n1表示度为1的结点数,则树T的结点总数n=n0+n1+n2,我们再换个角度,看一下树T的连接线数,除了根节点,其他结点都有一根线表示分支进入,所以连接线数为结点总数减去1。按连接线树算的话:n-1=n1+2n2,可推导出n0+n1+n2-1=n1+2n2,继续推导可得n0=n2+1
性质4:具有n个结点的完全二叉树的深度为(这里的[]是向下取整)
性质5:如果对一颗有n个结点的完全二叉树(其深度为)的结点按层序编号(从第1层到第
层,每层从左到右),对任一结点i(1<=i<=n)有:
(1)如果 i = 1,则结点 i 是二叉树的根,无双亲;如果 i > 1,则其双亲是结点[i/2]
(2)如果 2i > n,则结点 i 无孩子(结点 i 为叶子结点);否则其左孩子是结点 2i
(3)如果 2i+1 > n ,则结点i无右孩子;否则其右孩子是结点 2i+1
5.二叉树的存储:顺序存储、链式存储
(1)二叉树的顺序存储结构缺点很明显:不能反应逻辑关系;对于特殊的二叉树(左斜树、右斜树),浪费存储空间。所以二叉树顺序存储结构一般只用于完全二叉树
(2)二叉树的链式存储
//二叉树的二叉链表存储表示
typedef struct BiTNode{
//结点数据域TElemType data;
//左右孩子指针struct BiTNode *1child,*r1child;
}BiTNode,*BiTree;
二、二叉树的遍历
二叉树的遍历:按某条搜索路径访问二叉树中每一个结点,使得每个结点被访问一次且仅被访问一次。遍历方法有4种:先序遍历,中序遍历,后序遍历,层次遍历
1.先序遍历
(1)访问根节点
(2)先序遍历左子树
(3)先序遍历右子树
先序遍历序列(根左右):abcdfge
2.中序遍历
(1)中序遍历左子树
(2)访问根节点
(3)中序遍历右子树
中序遍历序列(左根右):bafgdce
3.后序遍历
(1)后序遍历左子树
(2)后序遍历右子树
(3)访问根结点
后序遍历序列(左右根):bgfdeca
简便方法:
4.层序遍历
按层次(1-k层),每层从左到右依次访问二叉树中的每个结点
层次遍历序列:abcdefg
eg:已知二叉树先序遍历序列是:abcdefg;中序遍历序列是:cbdaefg
(1)画出该二叉树
(2)写出后序遍历序列
cdbgfea
三、哈夫曼树
1.基本概念识记
(1)路径:从一个结点到另一个结点之间的分支序列
(2)路径长度:从一个结点到另一个结点所经过的分支数目
(3)结点的权:根据应用的需要可以给树的结点赋权值
(4)结点的带权路径长度:从根到该结点的路径长度与该结点权的乘积
(5)树的带权路径长度:树中所有叶子结点的带权路径之和
其中,n是树的叶结点个数,wk是第k个叶子的权,lk是第k个叶子到根的路径长度。
(6)哈夫曼树:由n个带权叶子结点构成的所有二叉树中带权路径长度最短的二叉树
n个叶子结点的哈弗曼树有(2n-1) 个结点
在构造哈弗曼树时,是从叶子结点向根节点的方向进行的,每次都是两个两个成对的结点来形成一个新的分支结点,所以不存在度为1的结点。
2.哈夫曼树的构造
对于有n个叶子结点,可以构造出多个二叉树。但Huffman树是一个带权路径长度最小的二叉树,又称最优二又树。方法:
(1)将{w1,w2.,…,wn}看成n个二叉树;
(2)选择2个根结点的值最小的二叉树,构造1个新的二叉树;......; 直至剩1个树止。
eg:某系统在通信联络中只可能出现8个字符,其出现概率分别是:
Z K F C U D L E
2 7 24 32 37 42 42 120
请构造哈夫曼树
(1)排序:
(2)依次选取两个最小的连在一起
进行排版:
3.哈夫曼编码
前缀码:如果在一个编码系统中,任一个编码都不是其他任何编码的前缀,则称该编码系统中的编码是前缀码。例如,一组编码01,001,010,100,110就不是前缀码,因为01是010的前缀,若去掉01或010就是前缀码。
哈夫曼编码:对一棵具有n个叶子的哈夫曼树,若对树中的每个左分支赋予0,右分支赋子1,则从根到每个叶子的通路上,各分支的赋值分别构成一个二进制串,该二进制串就称为哈夫曼编码。
哈夫曼编码是最优前缀码
四、习题
答案:A
解释:因为二叉树有左孩子、右孩子之分,故一棵树转换成二叉树之后,这棵二叉树的形态是唯一的
答案:D
解释:枚举法
答案:D
解释:设度为0结点((叶子结点)个数为A,度为1的结点个数为B,度为2的结点个数为C,有A=C+1,A+B+C=1001,可得2C+B=1000,由完全二叉树的性质可得B=0或1,又因为C为整数,所以B=0,C=500,A=501,即有501个叶子结点。
答案:C
解释:若每层仅有一个结点,则树高h为1025;且其最小树高为[log2 1025]+1=11,即h在11至1025之间。
答案:A
解释:深度为h的满m叉树共有 m的h次方-1 个结点,第k层有 m的k次方-1 个结点
答案:C
解释:因为先序遍历结果是“根左右”,后序遍历结果是“左右根”,当没有左子树时,就是“根右”和“右根”;当没有右子树时,就是“根左”和“左根”。则所有的结点均无左孩子或所有的结点均无右孩子均可,所以A、B不能选又所有的结点均无左孩子与所有的结点均无右孩子时,均只有一个叶子结点,故选C。
答案: B
解释:在哈夫曼树中没有度为1的结点,只有度为0(叶子结点)和度为2的结点。设叶子结点的个数为n0,度为2的结点的个数为n2,由二叉树的性质n0=n2+1,则总结点数n=n0+n2=2*n0-1,得到n0=100。
答案:A
解释:哈夫曼树的构造过程是每次都选取权值最小的树作为左右子树构造一棵新的二叉树,所以树中一定没有度为1的结点、两个权值最小的结点一定是兄弟结点、任一非叶结点的权值一定不小于下一层任一结点的权值