PAT 甲级 1020 Tree Traversals

PAT 甲级 1020 Tree Traversals

给定二叉树的后序和中序遍历,输出二叉树的层序遍历(二叉树每个节点的值不同)

用index记录树中每个节点所在的位置,从0开始

用map记录节点信息,index为key,这样map自动从0开始排序,只需迭代输出map存储的值即可完成层序遍历

后序遍历的最后一个节点是子树的根节点,通过根节点的值,可在中序遍历中把子树分为左子树和右子树

后序遍历中左子树的根节点位置为root-(end - i + 1),即根节点位置-(右子树节点个数 + 1)

后序遍历中右子树的根节点位置为 root - 1,即根节点位置 - 1

i是中序遍历中根节点位置,end是中序遍历中最后一个元素位置

所以end - i为右子树节点个数

// 1020 Tree Traversals.cpp : 此文件包含 "main" 函数。程序执行将在此处开始并结束。
//

#include <iostream>
#include <vector>
#include <map>
using namespace std;
vector<int> post, in;
map<int, int> m;

void pre(int root, int start, int end, int index) {
    if (start > end) return;
    int i = start;
    while (i < end && in[i] != post[root]) i++;
    m[index] = post[root];
    pre(root - end + i - 1, start, i - 1, 2 * index + 1);
    pre(root - 1, i + 1, end, 2 * index + 2);
}
int main()
{
    int n;
    cin >> n;
    post.resize(n);
    in.resize(n);
    for (int i = 0; i < n; i++) cin >> post[i];
    for (int i = 0; i < n; i++) cin >> in[i];
    pre(n - 1, 0, n - 1, 0);
    auto it = m.begin();
    cout << it->second;
    while (++it != m.end()) cout << " " << it->second;
    return 0;
}


resize和reserve

esize(),设置大小(size);
reserve(),设置容量(capacity);
size()是分配容器的内存大小,而capacity()只是设置容器容量大小,但并没有真正分配内存。
打个比方:正在建造的一辆公交车,车里面可以设置40个座椅(reserve(40);),这是它的容量,但并不是说它里面就有了40个座椅,只能说明这部车内部空间大小可以放得下40张座椅而已。而车里面安装了40个座椅(resize(40)😉,这个时候车里面才真正有了40个座椅,这些座椅就可以使用了。

已知后序中序输出前序

和本题的思路一模一样,只是不需要记录index,当找到根节点时直接输出,然后分别输出左子树的前序遍历和右子树的前序遍历

#include <cstdio>
using namespace std;
int post[] = {3, 4, 2, 6, 5, 1};
int in[] = {3, 2, 4, 1, 6, 5};
void pre(int root, int start, int end) {
    if(start > end) return ;
    int i = start;
    while(i < end && in[i] != post[root]) i++;
    printf("%d ", post[root]);
    pre(root - 1 - end + i, start, i - 1);
    pre(root - 1, i + 1, end);
}
 
int main() {
    pre(5, 0, 5);
    return 0;
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值