二叉树的遍历
二叉树的遍历
本文中会用到栈和队列两种数据结构,先放在这里
/**
*
* 以二叉树节点为元素的循环队列,用于实现二叉树的层序遍历
*
*/
struct TQueue {
int front;
int rear;
BNode** elem;
};
//初始话一个队列
void InitTQueue(TQueue& queue);
//入队
int EnTQueue(TQueue& queue, BNode* x);
//出队
BNode* DeTQueue(TQueue& queue);
//队列是否为空
int isQueueEmpty(TQueue& queue);
//队列是否满了
int isQueueFull(TQueue& queue);
/**
*
* 以二叉树节点为元素的栈,用于实现二叉树的中序非递归遍历
*
*/
struct TStack {
BNode** elem;
int top;
};
//创建栈
TStack creakAStack();
//栈是否为空
int isStackEmpty(TStack stack);
//站是否满
int isStackFull(TStack stack);
//入栈
int Push(TStack& stack, BNode* element);
//出栈
BNode* Pop(TStack& stack);
/**
* 二叉树节点结构体的定义和二叉树相关函数的声明
*/
struct BNode
{
BNode* left;
BNode* right;
int val;
};
//按照中序序列生成二叉树
//如:ABD#G###CE##FH###
BNode* CreateTree();
//中序
void InOrder(BNode* root);
//先序
void PreOrder(BNode* root);
//后序
void PostOrder(BNode* root);
//中序非递归
void IterInorder(BNode* root);
//层序遍历
void LevelOrder(BNode* root);
//求叶节点
int Leaf(BNode* root);
//度为1
int NodesOne(BNode* root);
//度为2
int NodesTwo(BNode* root);
//节点数
int Nodes(BNode* root);
//树的高度
int Height(BNode* root);
//表达式求值
//例如:+1##/*6##3##2##
int Eval(BNode* root);
二叉树是一种递归定义,每一个非空节点都可以有0到2个节点,不断向下递归下去。因此在处理上面二叉树的常见问题时,递归非常常见
创建一个二叉树
//ABD#G###CE##FH###
BNode* CreateTree()
{
BNode* bt;
char ch;
scanf("%c", &ch);
if (ch == '#')bt = nullptr;
else {
MALLOC(bt, sizeof(BNode), BNode*);
bt->val = ch;
bt->left = CreateTree();
bt->right = CreateTree();
}
return bt;
}
这个函数中,视#为空,使用中序序列初始话一颗二叉树
二叉树的中序,先序、后续遍历
void InOrder(BNode* root)
{
if (root != nullptr) {
InOrder(root->left);
printf("%c", root->val);
InOrder(root->right);
}
}
void PreOrder(BNode* root)
{
if (root != nullptr) {
printf("%c", root->val);
InOrder(root->left);
InOrder(root->right);
}
}
void PostOrder(BNode* root)
{
if (root != nullptr) {
InOrder(root->left);
InOrder(root->right);
printf("%c", root->val);
}
}
中序非递归遍历
void IterInorder(BNode* root)
{
BNode* temp;
temp = root;
TStack stack = creakAStack();
while (temp!= nullptr) {
while (temp!=nullptr) {
Push(stack, temp);
temp = temp->left;
}
if (!isStackEmpty(stack)) {
temp = Pop(stack);
printf("%c", temp->val);
}
temp = temp->right;
}
}
中序非递归遍历用到了栈,思路和中序递归差不多,只不过用栈来保存之前经过的节点。
从根节点不断向左走,直到为空,将节点都压入栈中。
之后不断将节点从栈中弹出,将这个节点访问之后,在转向他的右节点。
层序遍历
void LevelOrder(BNode* root)
{
TQueue queue;
InitTQueue(queue);
BNode* temp=nullptr;
EnTQueue(queue, root);
while (!isQueueEmpty(queue)) {
temp = DeTQueue(queue);
printf("%c", temp->val);
if (temp->left != nullptr) {
EnTQueue(queue, temp->left);
}
if (temp->right != nullptr) {
EnTQueue(queue, temp->right);
}
}
}
层序遍历就是将二叉树一层一层遍历掉。如何实现呢。这里用到了队列:
先将根节点入队,然后开始循环,根节点出队,如果左节点不为空,左节点入队,右节点不为空,右节点入队。再次让一个节点出队,再做如此处理,直到最后一层。
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· AI与.NET技术实操系列:向量存储与相似性搜索在 .NET 中的实现
· 基于Microsoft.Extensions.AI核心库实现RAG应用
· Linux系列:如何用heaptrack跟踪.NET程序的非托管内存泄露
· 开发者必知的日志记录最佳实践
· SQL Server 2025 AI相关能力初探
· winform 绘制太阳,地球,月球 运作规律
· 震惊!C++程序真的从main开始吗?99%的程序员都答错了
· AI与.NET技术实操系列(五):向量存储与相似性搜索在 .NET 中的实现
· 超详细:普通电脑也行Windows部署deepseek R1训练数据并当服务器共享给他人
· 【硬核科普】Trae如何「偷看」你的代码?零基础破解AI编程运行原理