纸上得来终觉浅,绝知此事要躬行。大家好!我是霜淮子,欢迎订阅我的专栏《算法系列》。
学习经典算法和经典代码,建立算法思维;大量编码让代码成为我们大脑的一部分。
⭐️已更系列
1、基础数据结构
1.1、链表➡传送门
1.2、队列➡传送门
1.3、 栈 ➡传送门
1.4、二叉树
专栏直达《算法系列》
前言
目录
树是非线性数据结构,它能很好的描述数据的层次关系。这种结构在现实中也很常见,如文件目录,书本的目录就是典型的树型结构。二叉树是最常见的树型结构,特别适合编码,常常将一般的树转化为二叉树来处理。
1.4.1、二叉树的概念
1、二叉树的性质
二叉树的每个节点最多有两个子节点,分别称为左孩子、右孩子,以它们为根的子树称为左子树、右子树。
二叉树每层节点数以2的倍数递增,所以二叉树的第i层最多有2的i-1次方个节点。
如果每层的节点数都是满的,称它为满二叉树。
二叉树的一些优势:
- 在二叉树上能进行极高效率的访问。
- 二叉树很适合做从整体到局部、从局部到整体的操作。
- 基于二叉树的算法容易设计和实现。
2、二叉树的存储结构
二叉树的一个节点的存储、包括节点的值、左右子节点,有动态和静态两种存储方法。
(1)、动态二叉树。数据结构中一般这样定义二叉树:
struct Node{
int value; //节点的值,可以定义多个值
node * lson, *reon; //指向左右子节点
};
动态新建一个Node时,用new运算符动态申请一个节点。使用完毕后,应该用delete命令释放它,否则会内存泄漏。动态二叉树的优点是不浪费空间;缺点是需要管理,不小心会出错。
(2)、用静态数组存储二叉树。
struct Node{
char value;
int lson,rson;
}tree[N];
1.4.2、二叉树的遍历
1、宽度优先遍历
有时需要按层次一层层从上到下遍历二叉树。
需按E-BG-ADFI-CH的顺序访问时用宽度优先搜索(BFS)最合适。
2、深度优先遍历
用深度优先搜索(DFS)遍历二叉树。
按深度搜索的顺序访问二叉树,对父节点、左孩子、右孩子进行组合,有先序遍历、中序遍历、后序遍历这三种访问顺序,
(1)、先序遍历,按父节点、左孩子、右孩子的顺序访问。输出序号是EBADCGFIH,先遍历的第一个节点是根。
伪代码如下:
void preorder (node * root){
cout<<root->value; //输出
preorder(root->lson);//递归左子树
preorder(root->rson);//递归右子树
}
(2)、中序遍历、 按左节点、父节点、右孩子的顺序访问。中序遍历的输出顺序是ABCDEFGHI。
伪代码如下:
void inorder(node * root){
inorder(root->lson);//递归左子树
cout<<root->value;//递归右子树
inorder(root->rson);//输出
}
(3)、后序遍历,按左孩子、右孩子、父节点的顺序访问。后序遍历输出的顺序是ACDBFHIGE。后序遍历的最后一个节点是根。
伪代码如下:
void postorder(node * root){
postorder(root->lson);
postorder(root->rson);
cout<<root->value;
}
如果已知某科二叉树的中序遍历和另一种遍历,可以把这棵树构造出来,即”中序遍历+后序遍历“或”中序遍历+先序遍历“,都能确定一颗树。
但是,如果不知道中序遍历,只有先序遍历和后序遍历,则不能确定一颗二叉树。
-END-