数据结构Review 第五章-树与二叉树(1)

一. 树的定义和基本术语

e86a1b4437d5448bb62b582ee93e78ba.jpeg

1. 结点之间的关系描述

①祖先结点   ②子孙结点   ③父结点(双亲结点)   ④孩子结点   ⑤兄弟结点   ⑥堂兄弟结点

路径:只能从上往下

路径长度:经过几条边

2. 结点、树的属性描述

属性:结点的深度(层次)——从上往下数

           结点的高度——从下往上数

           树的高度(深度)——总共有多少层

           结点的度——有几个分支结点(类似于出度)

           树的度——各结点的度的最大值

3. 有序树 VS 无序树

有序树:各子树从左至右是有次序的

无序树:各子树从左至右是无序的

森林:由m (m>=0)棵树组成

4. 树的性质

① 结点数=总度数+1

② 度为m的树、m叉树的区别66626a5c00b6498ea5b2edf61ab69d10.jpeg

③ m叉树、度为m的树第i层至多有eq?m%5E%7Bi-1%7D个结点(i>=1)

④ 高度为h的m叉树至多有eq?%5Cfrac%7Bm%5Eh-1%7D%7Bm-1%7D个结点

     等比数列求和公式:eq?a+aq+...+aq%5E%7Bn-1%7D%3D%5Cfrac%7Ba%281-q%5En%29%7D%7B1-q%7D

⑤ 高度为h的m叉树至少有h个结点

     高为h、度为m的树至少有h+m-1个结点

⑥ 具有n个结点的m叉树的最小高度为 eq?%24%5Clceil%20log_%7Bm%7D%28n%28m-1%29+1%29%29%20%5Crceil%24

2cb9c161846b40acaf517d112ddd0596.jpeg

二. 二叉树的定义和基本概念

每个结点至多两棵子树,左右子树不可颠倒(有序树)

1. 几个特殊的二叉树

①满二叉树:高度为h,含有eq?2%5Eh-1个结点的二叉树;按层序从1开始编号,结点i的左孩子为2i,右孩子为2i+1;结点的父节点为2%20%5Crfloor%24

②完全二叉树:每个结点编号与满二叉树对应的树。

         特点:i)最后两层可能有叶子结点

                    ii)最多只有一个度为1的结点

                    iii)i<=2%20%5Crfloor%24为分支结点,i>=2%20%5Crfloor%24为叶子结点

c6fd43bfa118447b9440347a2e73fac5.jpeg

③二叉排序树

左子树上所有结点的关键字均小于根节点的关键字

右子树上所有结点的关键字均大于根节点的关键字

左子树和右子树有分别各是一棵二叉排序树

“左小右大”,常用于元素的排序、搜索

b21243bb783747d19ec8f6bf5e7a8a19.jpeg

④平衡二叉树

树上任何一结点的左子树和右子树的深度之差不超过1

平衡二叉树能有更高的搜索效率

平衡因子:此结点往下,左子树深度-右子树深度

471a78fbcfc34b68b7647cc21a3a8521.jpeg

2. 二叉树的性质

①二叉树中,度为0的结点比度为2的结点多1个(叶子结点比二分支结点多一个

②二叉树第i层至多eq?2%5Ei-1个结点

③高度为h的二叉树至多有eq?2%5Eh-1个结点

④对于完全二叉树,度为1的结点只有0或者1个(单分支结点只有一个

三. 二叉树的存储结构

1. 二叉树的顺序存储

一定要把二叉树结点的编号与完全二叉树对应起来

dd6510304d394b90b0f5cfafb1afa621.jpeg

/*二叉树的顺序存储*/
#define MaxSize 100
//一定要把二叉树的结点编号与完全二叉树对应起来
struct TreeNode {
	ElemType value;
	bool isEmpty;
};
TreeNode t[MaxSize];
for (int i = 0; i < MaxSize; i++) {
	t[i].isEmpty = true;
}

2. 二叉树的链式存储

/*二叉树的链式存储*/
typedef struct BiTNode {//n个结点的二叉链表有n+1个空链域
	ElemType data;
	struct BiTNode* lchild, * rchild;
	//若常访问父结点,可追加定义一个*parent,成为三叉链表,否则从根节点遍历会很耗时间
}BiTNode,BiTree;
//初始化树
BiTree root = NULL;
//插入根结点
root = (BiTree)malloc(sizeof(BiTNode));
root->data = { 1 };
root->lchild = NULL;
root->rchild = NULL;
//插入新结点
BiTNode* p = (BiTNode*)malloc(sizeof(BiTNode));
p->data = { 2 };
p->lchild = NULL;
p->rchild = NULL;
root->lchild = p;

四. 二叉树的先中后序遍历

1. 二叉树的遍历

①先序:根左右        ②中序:左根右        ③后序:左右根

0b5f333cfedf4bfcb883c96c0b618438.jpeg

2. 先序遍历(代码)

/*先序遍历*/
void PreOrder(BiTree T) {
	if (T != NULL) {
		visit(T);//访问根结点
		PreOrder(T->lchild);
		PreOrder(T->rchild);
	}
}

T(n) = O(h+1) =O(h),h为树的高度,+1是因为叶子结点还会被当作有两个空子树。

五. 二叉树的层序遍历

1. 算法思想

①初始化一个辅助队列;②根结点入队;③若队列非空,队头出队并访问该结点,并将其左右孩子插入队尾;④重复③直到队空。

2. 代码实现

/*二叉树的层序遍历*/
void LevelOrder(BiTree T) {
	LinkQueue Q;
	InitQueue(Q);
	BiTree p;
	EnQueue(Q, T);
	while (!IsEmpty(Q)) {
		DeQueue(Q, p);
		visit(p);
		if (p->lchild != NULL)EnQueue(Q, p->lchild);
		if (p->rchild != NULL)EnQueue(Q, p->rchild);
	}
}

六. 由遍历序列构造二叉树

1. 由遍历序列构造二叉树

若只给出一棵二叉树的前、中、后、层序遍历序列中的一种,不能唯一确定一棵二叉树。

需要中序与其他任意一种遍历序列才能唯一确定

078125a7dac845669989fcb0c076497e.jpeg

七. 由遍历序列构造二叉树

7d612f96f07f453d97d9b284396e0c7c.jpg

 八. 线索二叉树的概念872f5c1deff04b7ba85bf654b06cf814.jpg

 九. 二叉树的线索化

9ff2bcfde1c84b23b8475c1588eb0898.jpg

十. 线索二叉树找前驱/后继

83c19c761f79477abfdac52f8215ca12.jpg  259a7fdbb4f34df593519c16e780c7d0.jpg

 d781f12869f1466a8e6d66c254b6539a.jpg

04be10cecb2d4cb6b9e0cea9070aa7b5.jpg

 

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

WISHMELUCK1'

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值