二叉树的链式结构和递归程序的递归流程图

二叉树的链式存储结构是指,用链表来表示一棵二叉树,即用链来指示元素的逻辑关系。 通常的方法是链表中每个结点由三个域组成,数据域和左右指针域,左右指针分别用来给出该结点左孩子和右孩子所在的链结点的存储地址 。链式结构又分为二叉链和三叉链,当前学习二叉链。

普通二叉树的增删查改没有意义。如果是为了存储数据,线性表更简单,二叉树更复杂,并且插入删除也不好定义。有意义的是通过二叉树引出搜索树,搜索树又有AVL树和红黑树。再搜索树中查找一个节点最多找高度次。

深度优先:前中后序遍历 一般借助递归

广度优先:层序遍历 一般借助队列

c 复制代码
typedef char BTDataType;
typedef struct BinaryTreeNode
{
	BTDataType data;
	struct BinaryTreeNode* left;
	struct BinaryTreeNode* right;
}BTNode;
 // 二叉树前序遍历 递归
void PrevOrder(BTNode* root)
{
	if(root == NULL)
	{
		printf("NULL ");
		return;
	}
	// 根 左 右子树 递归 递归过程图在下方
	printf("%c ",root->data);
	PrevOrder(root->left);
	PrevOrder(root->right);
}
 // 二叉树中序遍历
void InOrder(BTNode* root)
{
	if(root == NULL)
	{
		printf("NULL ");
		return;
	}
	// 左 根 右子树 递归 递归过程图在下方
	InOrder(root->left);
	printf("%c ",root->data);
	InOrder(root->right);
}
 // 二叉树后序遍历
void PostOrder(BTNode* root)
{
	if(root == NULL)
	{
		printf("NULL ");
		return;
	}
	// 左 右 根 递归 递归过程图在下方
	PostOrder(root->left);
	PostOrder(root->right);
	printf("%c ",root->data);
}
// 求节点的个数
int TreeSize(BTNode* root)
{
	// root不是NULL,则个数为左节点个数+右节点个数+1(加的1就是对本节点个数加上去)
	return root == NULL ? 0 : TreeSize(root->left) + TreeSize(root->right) + 1;
}
// 求叶子结点的个数 
// 1.NULL return 0 2.叶子 return 1 3.非空且不是叶子 reutrn 左子树叶子节点个数+右子树叶子节点个数
int TreeLeefSize(BTNode* root)
{
	if(root == NULL)
		return 0;
	if(root->left == NULL && root->right == NULL)
		return 1;
	return TreeLeefSize(root->left) + root->left(root->right);
}
// 求第K层节点的个数 设K=3 化解为左子树的第K-1(2)层和右子树的第k -1(2)层
int TreeKLeefSize(BTNode* root, int k)
{
	if(root == NULL)
		return 0;
	if(k == 1)
		return 1;
	return TreeKLeefSize(root->left, k-1) + TreeKLeefSize(root->right, k-1);
}
// 查找树里面值为X的那个节点 1.root == NULL return NULL 
// 2.root 不是要找的 先找左树 左树如果没有再找右树 3.左右都没有则当前树没找到 return null
BTNode* TreeFind(BTNode* root, BTDataType x)
{
	if(root == NULL)
		return NULL;
	
	// 我就是x则返回
	if(root->data == x)
	{
		return root;
	}
	
	// 不是x先在左边找再在右边找
	BTNode* lret = TreeFind(root->left, x); // 找到了返回root 没找到返回NULL
	if(lret)
		return lret;
		
	BTNode* rret = TreeFind(root->right, x); // 找到了返回root 没找到返回NULL
	if(rret)
		return rret;
		
	// 左右都没找到
	return NULL;
}
// 二叉树销毁 形参的改变不会影响实参,因此需要二级指针
void BinaryTreeDestory(BTNode** pproot)
{
    // if(*pproot == NULL)
	// 	return;
	// BinaryTreeDestory(&(*pproot)->left); //先将二级指针转换为一级再取地址变为2级传参
	// BinaryTreeDestory(&(*pproot)->right);
	// free(*pproot);
	// *pproot== NULL;
}
// 一级指针的做法 存在野指针,需要将野指针置空 保持接口一致性
void BinaryTreeDestory(BTNode* root)
{
	if(root == NULL)
		return;
	BinaryTreeDestory(root->left); //先将二级指针转换为一级再取地址变为2级传参
	BinaryTreeDestory(root->right);
	free(root);
}
// 创建节点
BTNode* CreateTreeNode (BTDataType x)
{
	BTNode* n1 = (BTNode*)malloc(sizeof(BTNode));
	n1->data = x;
	n1->left = NULL;
	n1->right = NULL:
	return node;
}
int main()
{
	// 手动连接上图中的树
	BTNode* A = CreateTreeNode('A');
	BTNode* B = CreateTreeNode('B');
	BTNode* C = CreateTreeNode('C');
	BTNode* D = CreateTreeNode('D');
	BTNode* E = CreateTreeNode('E');
	BTNode* F = CreateTreeNode('F');
	A->left = B;
	A->right = C;
	B->left = D;
	C->left = E;
	c->right = F;
	// 二级做法BinaryTreeDestory(&A);
	// 一级做法
	BinaryTreeDestory(A);
	A = NULL;
}

下图为PrevOrder的递归过程图。函数调用该板块完成后会返回到使用该板块的语句。前中后序的本质是一样的,就是打印的时机不同。

  1. 求节点的个数(前序) 1+左树节点个数+右树节点个数
  2. 求树的高度(后序) max(左树的高度,右树的高度)+1

深度优先:前中后序遍历 一般借助递归

广度优先:层序遍历 一般借助队列

相关推荐
csdn_aspnet1 小时前
C/C++ 两个凸多边形之间的切线(Tangents between two Convex Polygons)
c语言·c++·算法
豆豆的java之旅3 小时前
软考中级软件设计师 数据结构详细知识点(含真题+练习题,可直接复习)
java·开发语言·数据结构
北顾笙9803 小时前
day07-数据结构力扣
数据结构
兰.lan3 小时前
【黑马ai测试】判定表+流程图+ai生成测试用例
ai·测试用例·流程图·ai编程
似水এ᭄往昔4 小时前
【数据结构】--链表OJ
数据结构·算法·链表
剑心诀4 小时前
02 数据结构(C) | 线性表——顺序表的基本操作
c语言·开发语言·数据结构
m0_488633324 小时前
Windows环境下编译运行C语言程序,合适工具与方法很关键
c语言·windows·git·开发工具·编译器
Book思议-5 小时前
【数据结构实战】C语言实现栈的链式存储:从初始化到销毁,手把手教你写可运行代码
数据结构·算法·链表··408
m0_488633325 小时前
C语言变量命名规则、入门自学、运算符优先级及数据结构介绍
c语言·数据结构·运算符优先级·变量命名·入门自学
左左右右左右摇晃5 小时前
数据结构——栈
数据结构·笔记