前置内容
typedef struct BiTNode { char data; //数据域 struct BiTNode *lchild,*rchild; //结构体指针 分别代表左孩子节点和右孩子节点 }BiTNode,*BiTree;
typedef struct BiTNode BiTNode为 struct BiTNode 起别名
typedef struct BiTNode* BiTree为 struct BiTNode* 起别名
第一关 先序创建二叉树
任务描述
本关任务:设计一个算法,根据二叉树的先序遍历序列创建二叉树,平台会输入创建好的二叉树的中序遍历序列
编程要求
输入
二叉树的先序遍历序列,其中,叶子结点的左右空子树用#表示
输出
该二叉树的中序遍历序列
测试说明
平台会对你编写的代码进行测试:
测试输入:
ABD##E##CF##G##
预期输出:
DBEAFCG
#include<iostream>
using namespace std;
typedef struct BiTNode
{
char data;
struct BiTNode *lchild,*rchild;
}BiTNode,*BiTree;
void CreateBiTree(BiTree &T)
{
//根据键盘输入,创建二叉树,在此处填入代码
//先序创建二叉树
char c; //定义字符型变量,用于接收传入值
c = getchar(); //获取用户输入
if(c == '#'){
T = NULL; //若为#,代表空节点
}else{
T = new BiTNode; //创建一个新节点
T->data = c; //将输入的字符赋值给节点数据
CreateBiTree(T->lchild); //递归创建左子树
CreateBiTree(T->rchild); //递归创建右子树
}
}
第二关 两棵树是否相同
任务描述
本关任务:设计一个算法,判断两棵二叉树是否相同
编程要求
输入
两棵二叉树的先序遍历序列,其中,叶子结点的左右空子树用#表示
输出
是否相同
测试说明
平台会对你编写的代码进行测试:
测试输入:
ABD##E##CF##G##
ABD##E##CF##G##
预期输出:
两棵树相同
测试输入:
ABD##E##CF##G##
ABD##M##CF##G##
预期输出:
两棵树不相同
#include<iostream>
using namespace std;
typedef struct BiTNode
{
char data;
struct BiTNode *lchild,*rchild;
}BiTNode,*BiTree;
int CmpTree(BiTree T1,BiTree T2)
{
//判断两棵树是否完全相等
//在此处写入代码,相等返回1,不相等返回0
//若两树都为空,相等
if(T1 == NULL && T2 == NULL){
return 1;
}else if(T1 == NULL || T2 == NULL){ //一树为空,一树不为空,两树不等
return 0;
}
if(T1->data != T2->data){
return 0; //同一节点数据域不等,两树不等
}
return CmpTree(T1->lchild,T2->lchild) && CmpTree(T1->rchild,T2->rchild); //比较左右孩子节点
}
视频链接:【数据结构】判断两棵树是否相等_哔哩哔哩_bilibili
第三关 合并两棵二叉树
任务描述
本关任务:设计一个算法,将两棵二叉树进行合并,合并规则是:两棵树对应位置都存在的结点,就将结点值加起来,否则空的位置就由另一个树的结点来代替。例如:
编程要求
输入
两棵二叉树的先序遍历序列,其中,叶子结点的左右空子树用#表示
输出
合并后新树的先序遍历序列
测试说明
平台会对你编写的代码进行测试:
测试输入:
135###2##
21#4##3#7##
预期输出:
345457
#include<iostream>
using namespace std;
typedef struct BiTNode
{
int data;
struct BiTNode *lchild,*rchild;
}BiTNode,*BiTree;
BiTree MergeTree(BiTree T1,BiTree T2)
{
//返回合并后的树的根节点
//如果对应位置只有一棵树的结点存在,使用该结点作为合并后树的新结点
//如果对应位置两棵树的结点均存在,创建一个新结点用于合并后树的结点,值为两个结点的值之和
//在此处写入代码
//如果T1为空,返回T2
if(T1 == NULL){
return T2;
}
//如果T2为空,返回T1
if(T2 == NULL){
return T1;
}
//为了节省空间,把T1当作返回对象
//数据域相加
T1->data += T2->data;
//递归操作对应左右子树
T1->lchild = MergeTree(T1->lchild,T2->lchild);
T1->rchild = MergeTree(T1->rchild,T2->rchild);
return T1;
}
视频链接:一起操作两个二叉树?有点懵!| LeetCode:617.合并二叉树_哔哩哔哩_bilibili
第四关 交换二叉树左右孩子
任务描述
本关任务:设计一个算法,将二叉树每个结点的左右孩子都交换位置
编程要求
输入
二叉树的先序遍历序列,其中空结点用#表示
输出
交换左右孩子后的二叉树先序遍历序列
测试说明
平台会对你编写的代码进行测试:
测试输入:
ABD##E##CF##G##
预期输出:
ACGFBED
#include<iostream>
using namespace std;
typedef struct BiTNode
{
char data;
struct BiTNode *lchild,*rchild;
}BiTNode,*BiTree;
void SwapBiTree(BiTree &T)
{
//交换二叉树每个结点的左孩子和右孩子
//在此处填入代码
//若空树,直接返回
if(T == NULL){
return;
}
//交换左右子树
BiTree temp = T->lchild;
T->lchild = T->rchild;
T->rchild = temp;
//对左右子树通过递归进行相同操作
SwapBiTree(T->lchild);
SwapBiTree(T->rchild);
}
第五关 完全二叉树判断
任务描述
本关任务:设计一个算法,判断二叉树是否是完全二叉树
编程要求
输入
二叉树的先序遍历序列,其中空结点用#表示
输出
是否是完全二叉树,若是输出yes,否输出no
测试说明
平台会对你编写的代码进行测试:
测试输入:
ABD##E##CF##G##
预期输出:
yes
#include<iostream>
#include<queue>
using namespace std;
typedef struct BiTNode
{
char data;
struct BiTNode *lchild,*rchild;
}BiTNode,*BiTree;
int isCompleteTree(BiTree T)
{
//判断是否为完全二叉树,若是返回1,不是返回0
//可使用c++的queue模板库
//在此处填入代码
if (!T) return 1; // 空树是完全二叉树
queue<BiTree> q;
q.push(T);
bool foundNull = false; // 标记是否已经遇到空节点
while (!q.empty()) {
BiTree node = q.front();
q.pop();
if (node == nullptr) {
foundNull = true; // 发现空节点
} else {
if (foundNull) {
return 0; // 如果已经遇到空节点,但当前节点不是空节点,说明不是完全二叉树
}
// 继续遍历左右子树
q.push(node->lchild);
q.push(node->rchild);
}
}
return 1; // 遍历结束没有问题,说明是完全二叉树
}