当前位置:网站首页>信息学奥赛一本通 1339:【例3-4】求后序遍历 | 洛谷 P1827 [USACO3.4] 美国血统 American Heritage
信息学奥赛一本通 1339:【例3-4】求后序遍历 | 洛谷 P1827 [USACO3.4] 美国血统 American Heritage
2022-07-05 20:10:00 【君义_noip】
【题目链接】
ybt 1339:【例3-4】求后序遍历
洛谷 P1827 [USACO3.4] 美国血统 American Heritage
两题都是已知先序和中序遍历序列,求后序遍历序列
区别为:【ybt 1339】先输入先序遍历序列,再输入中序遍历序列。【洛谷 P1827】先输入中序遍历序列,再输入先序遍历序列。
【题目考点】
1. 二叉树
已知先序、中序边路序列,求后序遍历序列
【解题思路】
解法1:
假设输入的中序遍历序列为:DBAECH,先序遍历序列为ABDCEF。以该输入为例讨论问题解法。
当前要解决的问题是:已知先序、中序遍历序列,构建二叉树。
- 首先先序遍历中第一个字母为树的根结点的值(A)。
- 而后在中序遍历序列中找到根结点值(A)的位置,根结点值左边的序列(DB)是根结点的左子树的中序遍历序列。根结点值右边的序列(ECF)为根结点的右子树的中序遍历序列。
- 在先序遍历序列中根据左子树中序遍历序列的长度,找到左子树的先序遍历序列(BD),及右子树的先序遍历序列(CEF)。
- 递归调用“已知先序中序遍历序列求二叉树”的函数。现在已知根结点的左子树、右子树的先序、中序遍历序列,那么就可以构建出根结点的左子树与右子树(构建子树相对于构建以A为根结点的树,是小规模问题,递归求解大规模问题时,小规模问题的解被视为是已知的)
- 以A为根结点,接上构造好的左右子树,即完成了树的构建。
接下来对这棵树做后序遍历,即可得到树的后序遍历序列。
写法1:使用字符数组
输入先序遍历序列到s_pre,中序遍历序列到字符数组s_in。
函数createTree需要传入ml,mr,pl,pr,意为:由先序序列s_pre[pl]~s_pre[pr]与中序序列s_in[ml]~s_in[mr]构造一棵二叉树
根据上述算法,先在中序序列中找到先序序列第一个字符s_pre[pl]的位置,找到位置为i。那么左子树的中序遍历序列为s_in[ml]~s_in[i-1],长度为i-ml,在先序遍历序列中,从pl+1开始取长为i-ml的序列,最后一个元素的位置为pl+i-ml,那么左子树的先序遍历序列为s_pre[pl+1]~s_pre[pl+i-ml]。类似地,可以得到右子树的中序序列为s_in[i+1]~s_in[mr],先序序列为s_pre[pl+i-ml+1]~s_pre[pr]。
使用createTree分别生成左右子树,接在新分配出来的根结点的下面,就得到了这棵树。
递归出口为:先序与中序序列的下标范围一定有pl<=pr且ml<=mr,如果不满足这一条件,序列范围无意义,应该返回。
写法2:使用string类
思路与上述方法类似,不再赘述。
使用string类,可以使用substr成员函数来取子串。每次传入函数的先序、中序序列都是string类对象。
【题解代码】:ybt 1339:【例3-4】求后序遍历
写法1:使用字符数组
#include <bits/stdc++.h>
using namespace std;
#define N 1000
struct Node
{
char val;
int left, right;
};
Node node[N];
int p = 1;
char s_pre[105], s_in[105];//s_pre:先序遍历序列 s_in:中序遍历序列
//由先序序列s_pre[pl]~s_pre[pr]与中序序列s_in[ml]~s_in[mr]构造一棵二叉树,返回根结点
int createTree(int pl, int pr, int ml, int mr)
{
if(pl > pr || ml > mr)
return 0;
int np = p++, i;
node[np].val = s_pre[pl];
for(i = ml; i <= mr; ++i)
{
if(s_in[i] == s_pre[pl])
break;
}
node[np].left = createTree(pl + 1, pl + i - ml, ml, i - 1);
node[np].right = createTree(pl + i - ml + 1, pr, i + 1, mr);
return np;
}
void postOrder(int root)
{
if(root != 0)
{
postOrder(node[root].left);
postOrder(node[root].right);
cout << node[root].val;
}
}
int main()
{
cin >> s_pre >> s_in;
int root = createTree(0, strlen(s_pre) - 1, 0, strlen(s_in) - 1);
postOrder(root);
return 0;
}
写法2:使用string类
#include <bits/stdc++.h>
using namespace std;
#define N 1000
struct Node
{
char val;
int left, right;
};
Node node[N];
int p = 1;
string s_pre, s_in;
int createTree(string sp, string si)//用先序序列sp与中序序列si构建二叉树,返回树根
{
int np = p++, i;
node[np].val = sp[0];
for(i = 0; i < si.length(); ++i)
{
if(sp[0] == si[i])
break;
}
int len_l = i, len_r = si.length() - 1 - i;//左右子树序列长度
if(len_l > 0)//序列长度大于0,才可以建立一棵树
node[np].left = createTree(sp.substr(1, len_l), si.substr(0, len_l));
if(len_r > 0)
node[np].right = createTree(sp.substr(i+1, len_r), si.substr(i+1, len_r));
return np;
}
void postOrder(int root)
{
if(root != 0)
{
postOrder(node[root].left);
postOrder(node[root].right);
cout << node[root].val;
}
}
int main()
{
cin >> s_pre >> s_in;
int root = createTree(s_pre, s_in);
postOrder(root);
return 0;
}
【题解代码】:洛谷 P1827 [USACO3.4] 美国血统 American Heritage
写法1:使用字符数组
#include <bits/stdc++.h>
using namespace std;
#define N 1000
struct Node
{
char val;
int left, right;
};
Node node[N];
int p = 1;
char s_pre[105], s_in[105];//s_pre:先序遍历序列 s_in:中序遍历序列
//由先序序列s_pre[pl]~s_pre[pr]与中序序列s_in[ml]~s_in[mr]构造一棵二叉树,返回根结点
int createTree(int pl, int pr, int ml, int mr)
{
if(pl > pr || ml > mr)
return 0;
int np = p++, i;
node[np].val = s_pre[pl];
for(i = ml; i <= mr; ++i)
{
if(s_in[i] == s_pre[pl])
break;
}
node[np].left = createTree(pl + 1, pl + i - ml, ml, i - 1);
node[np].right = createTree(pl + i - ml + 1, pr, i + 1, mr);
return np;
}
void postOrder(int root)
{
if(root != 0)
{
postOrder(node[root].left);
postOrder(node[root].right);
cout << node[root].val;
}
}
int main()
{
cin >> s_in >> s_pre;
int root = createTree(0, strlen(s_pre) - 1, 0, strlen(s_in) - 1);
postOrder(root);
return 0;
}
写法2:使用string类
#include <bits/stdc++.h>
using namespace std;
#define N 1000
struct Node
{
char val;
int left, right;
};
Node node[N];
int p = 1;
string s_pre, s_in;
int createTree(string sp, string si)//用先序序列sp与中序序列si构建二叉树,返回树根
{
int np = p++, i;
node[np].val = sp[0];
for(i = 0; i < si.length(); ++i)
{
if(sp[0] == si[i])
break;
}
int len_l = i, len_r = si.length() - 1 - i;//左右子树序列长度
if(len_l > 0)//序列长度大于0,才可以建立一棵树
node[np].left = createTree(sp.substr(1, len_l), si.substr(0, len_l));
if(len_r > 0)
node[np].right = createTree(sp.substr(i+1, len_r), si.substr(i+1, len_r));
return np;
}
void postOrder(int root)
{
if(root != 0)
{
postOrder(node[root].left);
postOrder(node[root].right);
cout << node[root].val;
}
}
int main()
{
cin >> s_in >> s_pre;
int root = createTree(s_pre, s_in);
postOrder(root);
return 0;
}
边栏推荐
- Is it safe for CICC fortune to open an account online?
- leetcode刷题:二叉树14(左叶子之和)
- Where is the operation of new bonds? Is it safer and more reliable to open an account
- leetcode刷题:二叉树17(从中序与后序遍历序列构造二叉树)
- 强化学习-学习笔记4 | Actor-Critic
- 解决php无法将string转换为json的办法
- Is the education of caiqiantang reliable and safe?
- Analysis of openh264 decoded data flow
- Build your own website (16)
- Debezium series: idea integrates lexical and grammatical analysis ANTLR, and check the DDL, DML and other statements supported by debezium
猜你喜欢

Hong Kong stocks will welcome the "best ten yuan store". Can famous creative products break through through the IPO?

微信小程序正则表达式提取链接

Redis cluster simulated message queue

零道云新UI设计中

leetcode刷题:二叉树15(找树左下角的值)

Build your own website (16)

Win10 x64环境下基于VS2017和cmake-gui配置使用zxing以及opencv,并实现data metrix码的简单检测

计算lnx的一种方式

Rainbond 5.7.1 支持对接多家公有云和集群异常报警

【数字IC验证快速入门】7、验证岗位中必备的数字电路基础知识(含常见面试题)
随机推荐
Is it safe for CICC fortune to open an account online?
无卷积骨干网络:金字塔Transformer,提升目标检测/分割等任务精度(附源代码)...
E. Singhal and Numbers(质因数分解)
Process file and directory names
leetcode刷题:二叉树13(相同的树)
Float. The specific meaning of the return value of floattorawintbits is to convert float into byte array
leetcode刷题:二叉树14(左叶子之和)
After 95, Alibaba P7 published the payroll: it's really fragrant to make up this
【数字IC验证快速入门】1、浅谈数字IC验证,了解专栏内容,明确学习目标
ByteDance dev better technology salon was successfully held, and we joined hands with Huatai to share our experience in improving the efficiency of web research and development
2022年7月4日-2022年7月10日(ue4视频教程mysql)
C - sequential structure
银河证券在网上开户安全吗?
.Net分布式事务及落地解决方案
Solve the problem that the database configuration information under the ThinkPHP framework application directory is still connected by default after modification
【c语言】归并排序
BZOJ 3747 POI2015 Kinoman 段树
建立自己的网站(16)
Rainbond 5.7.1 支持对接多家公有云和集群异常报警
ROS2专题【01】:win10上安装ROS2