【数据结构】二叉树的顺序结构及链式结构

目录

1.树的概念及结构

1.1树的概念

1.2树的相关概念

​编辑

 1.3树的表示

 1.4树在实际中的运用(表示文件系统的目录树结构)

2.二叉树概念及结构

2.1二叉树的概念

2.2现实中的二叉树

​编辑 

2.3特殊的二叉树

2.4二叉树的性质

2.5二叉树的存储结构

3 .二叉树链式结构的实现

3.1二叉树的创建

3.2二叉树的遍历

3.21前序、中序以及后序遍历

3.22层序遍历


1.树的概念及结构

1.1树的概念

树是一种非线性的数据结构,它是由n(n>=0)个有限结点组成一个具有层次关系的集合。把它叫做树是因 为它看起来像一棵倒挂的树,也就是说它是根朝上,而叶朝下的。

  • 有一个特殊的结点,称为根结点,根节点没有前驱结点
  • 除根节点外,其余结点被分成M(M>0)个互不相交的集合T1、T2、……、Tm,其中每一个集合Ti(1<= i <= m)又是一棵结构与树类似的子树。每棵子树的根结点有且只有一个前驱,可以有0个或多个后继
  • 因此,树是递归定义的。

注意:树形结构中,子树之间不能有交集,否则就不是树形结构 

1.2树的相关概念

  • 节点的度:一个节点含有的子树的个数称为该节点的度; 如上图:A的为6
  • 叶节点或终端节点:度为0的节点称为叶节点; 如上图:B、C、H、I...等节点为叶节点
  • 非终端节点或分支节点:度不为0的节点; 如上图:D、E、F、G...等节点为分支节点
  • 双亲节点或父节点:若一个节点含有子节点,则这个节点称为其子节点的父节点; 如上图:A是B的父节点
  • 孩子节点或子节点:一个节点含有的子树的根节点称为该节点的子节点; 如上图:B是A的孩子节点
  • 兄弟节点:具有相同父节点的节点互称为兄弟节点; 如上图:B、C是兄弟节点
  • 树的度:一棵树中,最大的节点的度称为树的度; 如上图:树的度为6
  • 节点的层次:从根开始定义起,根为第1层,根的子节点为第2层,以此类推;
  • 树的高度或深度:树中节点的最大层次; 如上图:树的高度为4
  • 堂兄弟节点:双亲在同一层的节点互为堂兄弟;如上图:H、I互为兄弟节点
  • 节点的祖先:从根到该节点所经分支上的所有节点;如上图:A是所有节点的祖先
  • 子孙:以某节点为根的子树中任一节点都称为该节点的子孙。如上图:所有节点都是A的子孙 
  • 森林:由m(m>0)棵互不相交的树的集合称为森林; 

 1.3树的表示

树结构相对线性表就比较复杂了,要存储表示起来就比较麻烦了,既然保存值域,也要保存结点和结点之间 的关系,实际中树有很多种表示方式如:双亲表示法,孩子表示法、孩子双亲表示法以及孩子兄弟表示法 等。我们这里就简单的了解其中最常用的孩子兄弟表示法。

typedef int DataType;
struct Node
{struct Node* _firstChild1; // 第一个孩子结点struct Node* _pNextBrother; // 指向其下一个兄弟结点DataType _data; // 结点中的数据域
};

 1.4树在实际中的运用(表示文件系统的目录树结构)

 


 

2.二叉树概念及结构

2.1二叉树的概念

一颗二叉树的节点是一个有限的集合,该集合只有俩种可能:

1.为空指针

2.由一个根节点和俩个分别称为左子树和右子树的二叉组成

由上图可知:

1. 二叉树不存在度大于2的结点

2. 二叉树的子树有左右之分,次序不能颠倒,因此二叉树是有序树                                          注意:对于任意的二叉树都是由以下几种情况复合而成的:

2.2现实中的二叉树

 

 

2.3特殊的二叉树

1. 满二叉树:一个二叉树,如果每一个层的结点数都达到最大值,则这个二叉树就是满二叉树。也就是 说,如果一个二叉树的层数为K,且结点总数是2的k次方-1 ,则它就是满二叉树。

2. 完全二叉树:完全二叉树是效率很高的数据结构,完全二叉树是由满二叉树而引出来的。对于深度为K 的,有n个结点的二叉树,当且仅当其每一个结点都与深度为K的满二叉树中编号从1至n的结点一一对 应时称之为完全二叉树。 要注意的是满二叉树是一种特殊的完全二叉树。 

2.4二叉树的性质

1.若规定根节点的层数为1,则一颗非空二叉树的第i层最多有2(^2^-1)个结点。

2.若规定根节点的层数为1,则深度为h的二叉树的最大节点数是2(^h^)-1.

3.堆任何一颗二叉树,如果度为0其叶结点个数为n0,度为2的分支结点个数为n2,则有n0=n2+1.

4.若规定根节点的层数为1,则有n个结点的满二叉树的深度,h=log2(n+1).(ps:log2(n+1)是以2为底,n+1为对数)

5.对于具有n个节点的完全二叉树,如果按照从上至下从左至右的数组顺序对所有节点从0开始编号,则对于序号为i的节点有:

1. 若i>0,i位置节点的双亲序号:(i-1)/2;i=0,i为根节点编号,无双亲节点

2. 若2i+1=n否则无左孩子

3. 若2i+2=n否则无右孩子

2.5二叉树的存储结构

二叉树一般可以使用两种结构存储,一种顺序结构,一种链式结构。

1. 顺序存储 :顺序结构存储就是使用数组来存储,一般使用数组只适合表示完全二叉树,因为不是完全二叉树会有空间的浪费。而现实中使用中只有堆才会使用数组来存储,关于堆我们前面的章节有专门讲解。二叉树顺序存储在物理上是一个数组,在逻辑上是一颗二叉树。 

2. 链式存储 :二叉树的链式存储结构是指,用链表来表示一棵二叉树,即用链来指示元素的逻辑关系。 通常的方法是链表中每个结点由三个域组成,数据域和左右指针域,左右指针分别用来给出该结点左孩子和右孩子所在的链结点的存储地址 。链式结构又分为二叉链三叉链,当前我们学习中一般都是二叉链,后面会学到高阶数据结构如红黑树等会用到三叉链。 

 

typedef int BTDataType;
// 二叉链
struct BinaryTreeNode
{struct BinTreeNode* _pLeft; // 指向当前节点左孩子struct BinTreeNode* _pRight; // 指向当前节点右孩子BTDataType _data; // 当前节点值域
}
// 三叉链
struct BinaryTreeNode
{struct BinTreeNode* _pParent; // 指向当前节点的双亲struct BinTreeNode* _pLeft; // 指向当前节点左孩子struct BinTreeNode* _pRight; // 指向当前节点右孩子BTDataType _data; // 当前节点值域
};

 


3 .二叉树链式结构的实现

3.1二叉树的创建

 首先,我们这里先简单创建一个以中序遍历的二叉树结构,可以使用前序,中序,后序,下面会具体讲到遍历。

typedef struct BTNode
{char _data;struct BTNode* _left;struct BTNode* _right;
}BTNode;//中序遍历
void Inorder(BTNode* root)
{if(root){Inorder(root->_left);printf("%c ", root->_data);Inorder(root->_right);}
}BTNode* CreatBTree(char* str, int* pi)
{if(str[*pi]!= '#'){//当前节点非空,则创建当前节点BTNode*root=(BTNode*)malloc(sizeof(BTNode));root->_data = str[*pi];//字符位置向后移动一个位置++(*pi);//创建左子树root->_left=CreatBTree(str,pi);//字符位置向后移动一个位置++(*pi);//创建右子树root->_right=CreatBTree(str,pi);return root;}elsereturn NULL;  //如果是空节点,则返回NULL
}int main()
{char str[101];int i = 0;//读入字符串scanf("%s", str);//创建二叉树BTNode* root = CreatBTree(str, &i);//中序打印二叉树Inorder(root);printf("\n");return 0;
}

3.2二叉树的遍历

3.21前序、中序以及后序遍历

学习二叉树结构,最简单的方式就是遍历。所谓二叉树遍历(Traversal)是按照某种特定的规则,依次对二叉树中的节点进行相应的操作,并且每个节点只操作一次。访问结点所做的操作依赖于具体的应用问题。 遍历是二叉树上最重要的运算之一,也是二叉树上进行其它运算的基础。

按照规则,二叉树的遍历有:前序/中序/后序的递归结构遍历

1. 前序遍历(Preorder Traversal 亦称先序遍历)——访问根结点的操作发生在遍历其左右子树之前。

2. 中序遍历(Inorder Traversal)——访问根结点的操作发生在遍历其左右子树之中(间)。

3. 后序遍历(Postorder Traversal)——访问根结点的操作发生在遍历其左右子树之后。

由于被访问的结点必是某子树的根,所以N(Node)、L(Left subtree)和R(Right subtree)又可解释为 根、根的左子树和根的右子树。NLR、LNR和LRN分别又称为先根遍历、中根遍历和后根遍历。 

// 二叉树前序遍历
void PreOrder(BTNode* root);
// 二叉树中序遍历
void InOrder(BTNode* root);
// 二叉树后序遍历
void PostOrder(BTNode* root);

前序,中序和后序遍历图解:

 

3.22层序遍历

层序遍历:除了先序遍历、中序遍历、后序遍历外,还可以对二叉树进行层序遍历。设二叉树的根节点所在 层数为1,层序遍历就是从所在二叉树的根节点出发,首先访问第一层的树根节点,然后从左到右访问第2层 上的节点,接着是第三层的节点,以此类推,自上而下,自左至右逐层访问树的结点的过程就是层序遍历。 

 

// 层序遍历
void LevelOrder(BTNode* root);

 


本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://xiahunao.cn/news/2775416.html

如若内容造成侵权/违法违规/事实不符,请联系瞎胡闹网进行投诉反馈,一经查实,立即删除!

相关文章

c++新特性override和final

override 作用: 在子类中重写父类的虚函数&#xff0c;我们可以在子类的虚函数声明后加上override。 上图就在重写eat()的时候&#xff0c;加上override。 作用: 1. 可以提示读者&#xff0c;这个函数是重写自父类中的。 2. 加上override之后&#xff0c;我们在重…

数据库管理-第148期 最强Oracle监控EMCC深入使用-05(20240208)

数据库管理148期 2024-02-08 数据库管理-第148期 最强Oracle监控EMCC深入使用-05&#xff08;20240208&#xff09;1 性能主页2 ADDM Spotlight3 实时ADDM4 数据库的其他5 主机总结 数据库管理-第148期 最强Oracle监控EMCC深入使用-05&#xff08;20240208&#xff09; 作者&am…

实例分割论文阅读之:FCN:《Fully Convolutional Networks for Semantica Segmentation》

论文地址:https://openaccess.thecvf.com/content_cvpr_2015/papers/Long_Fully_Convolutional_Networks_2015_CVPR_paper.pdf 代码链接&#xff1a;https://github.com/pytorch/vision 摘要 卷积网络是强大的视觉模型&#xff0c;可以产生特征层次结构。我们证明&#xff0c…

Python解决SSL不可用问题

参考&#xff1a;https://blog.csdn.net/weixin_44894162/article/details/126342591 一、问题描述&#xff1a; 报错概述&#xff1a; WARNING: pip is configured with locations that require TLS/SSL, however the ssl module in Python is not available. ## 警告:pip配…

Project 2019下载安装教程,保姆级教程,附安装包和工具

前言 Project是一款项目管理软件&#xff0c;不仅可以快速、准确地创建项目计划&#xff0c;而且可以帮助项目经理实现项目进度、成本的控制、分析和预测&#xff0c;使项目工期大大缩短&#xff0c;资源得到有效利用&#xff0c;提高经济效益。软件设计目的在于协助专案经理发…

ubuntu原始套接字多线程负载均衡

原始套接字多线程负载均衡是一种在网络编程中常见的技术&#xff0c;特别是在高性能网络应用或网络安全工具中。这种技术允许应用程序在多个线程之间有效地分配和处理网络流量&#xff0c;提高系统的并发性能。以下是关于原始套接字多线程负载均衡技术的一些介绍&#xff1a; …

交通 | 共乘出行(下):基于图结构的动态多时空供需网络的均衡度量方法

博客&#xff1a;Alex Chin, & Tony Qin. (2023.02.25). Quantifying Efficiency in Ridesharing Marketplaces. Link: https://eng.lyft.com/quantifying-efficiency-in-ridesharing-marketplaces-affd53043db2 论文&#xff1a;Chin, Alex, and Zhiwei Qin. “A Unified…

Springboot根据环境读取application配置文件

目录 1. 首先创建两个不同配置文件 2. pom.xml 配置文件 3. 指定环境 4. 最后启动测试 1. 首先创建两个不同配置文件 分别为开发环境和生产环境 application-dev.properties 和 application-prod.properties application-dev.properties 配置为 1931 端口 application-pro…

CAN通讯协议详解

阅读引言&#xff1a; 本篇博文想给需要的人介绍一下CAN总线&#xff0c; 这个也算是我从B站学习记得笔记分享吧也算是。简单的介绍了CAN总线的大致内容&#xff0c; 简述支持CAN功能的STM32的简单使用例程。本视频的中的图片内容均来自B站爱上半导体博主的内容。 CAN高质量教学…

问题:在填制记账凭时,应注意以下几个方面:( ) #知识分享#其他

问题&#xff1a;在填制记账凭时&#xff0c;应注意以下几个方面&#xff1a;&#xff08; &#xff09; A:记账凭证各项内容必须完整 B:必须以审核无误的原始凭证为依据 C:记账凭证应连续编号 D:记账凭证的书写应清楚、规范。 参考答案如图所示

C++算法之双指针、BFS和图论

一、双指针 1.AcWing 1238.日志统计 分析思路 前一区间和后一区间有大部分是存在重复的 我们要做的就是利用这部分 来缩短我们查询的时间 并且在使用双指针时要注意对所有的博客记录按时间从小到大先排好顺序 因为在有序的区间内才能使用双指针记录两个区间相差 相当于把一个…

Leecode之随机链表的复制

一.题目及剖析 https://leetcode.cn/problems/copy-list-with-random-pointer/ 这个题目的意思就是拷贝一份复杂链表,难点在于它的random指针所指向的空间与拷贝下来的链表之间缺少一种联系,当然可以用遍历链表的方式通过value去找那块空间,不过时间复杂度太高. 二.思路引入 …

Redis Centos7 安装到启动

文章目录 安装Redis启动redis查看redis状况连接redis服务端 安装Redis 1.下载scl源 yum install centos-release-scl-rh2.下载redis yum install rh-redis5-redis 3. 创建软连接 1.cd /usr/bin 2. In -s /opt/rh/rh-redis5/root/usr/bin/redis-server ./redis-server 3. …

Ajax+JSON学习一

AjaxJSON学习一 文章目录 前言一、Ajax简介1.1. Ajax基础1.2. 同源策略 二、Ajax的核心技术2.1. XMLHttpRequest 类2.2. open指定请求2.3. setRequestHeader 设置请求头2.4. send发送请求主体2.5. Ajax取得响应 总结 前言 一、Ajax简介 1.1. Ajax基础 Ajax 的全称是 Asynchron…

雾计算:去中心化计算的未来之旅

雾计算是去中心化计算的基石&#xff0c;它将重塑我们的数字格局。通过使计算和存储更接近数据源&#xff0c;它改变了我们处理物联网生成数据的方式。通过雾计算探索未来&#xff0c;揭示了减少延迟、增强隐私和高效网络利用等好处。 随着传感器和可穿戴设备等物联网设备的数…

5.常量和数据类型(数字类型,字符串类型,模板字符串,布尔类型undefined,null检测数据类型),类型转化

什么是常量 常量就是不能改变的量&#xff0c;就是向计算机内存要一款空间然后存储的东西不能改变用const声明并且一定要初始化值 <!DOCTYPE html> <html lang"en"><head><meta charset"UTF-8"><meta http-equiv"X-UA-C…

基于LightGBM的回归任务案例

在本文中&#xff0c;我们将学习先进的机器学习模型之一&#xff1a;Lightgbm。在对XGB模型进行了越来越多的改进以获得更好的性能之后&#xff0c;XGBoost是一种极限梯度提升机器&#xff0c;但通过lightgbm&#xff0c;我们可以在没有太多计算的情况下实现类似或更好的结果&a…

【C++修行之道】(引用、函数提高)

目录 一、引用 1.1引用的基本使用 1.2 引用注意事项 1.3 引用做函数参数 1.4 引用做函数返回值 1.5 引用的本质 1.6 常量引用 1.7引用和指针的区别 二、函数提高 2.1 函数默认参数 2.2函数占位参数 2.3 函数重载 2.4函数重载注意事项 一、引用 1.1引用的基本使用 …

Ubuntu22.04 gnome-builder gnome C 应用程序习练笔记(二)

gnome-builder创建的程序&#xff0c;在工程树中有三个重要程序&#xff1a;main主程序、application应用程序和window主窗口程序。main整个程序的起始&#xff0c;它会操作application生产应用环境&#xff0c;application会操作window生成主窗口&#xff0c;于是就有了 appli…

Zookeeper集群搭建(3台)

准备工作 1、提前安装好hadoop102、hadoop103、hadoop104三台机器&#xff0c;参照&#xff1a;CentOS7集群环境搭建&#xff08;3台&#xff09;-CSDN博客 2、提前下载好Zookeeper安装包并上传到/opt/software上、安装包&#xff0c;链接&#xff1a;https://pan.baidu.com/…