2020-PTA总决赛-L2-3 完全二叉树的层序遍历(深搜+一维数组模拟二叉树)

一维数组模拟二叉树:

leftNode = root * 2
rightNode = root * 2 + 1
leftNode表示左孩子在一维数组中的下标(一维数组下标从1开始)
rightNode表示右孩子在一维数组中的下标
root表示根节点下标
比如完全二叉树层序遍历为10 2 5 6 8 7 3
那么用一维数组模拟后tree = [null, 10, 2, 5, 6, 8, 7, 3]
下标的数学关系一目了然:
下标为1的是10,它的左孩子是1 * 2的位置上的2,右孩子是1 * 2 + 1的位置上的5
下标为2的是2,它的左孩子是2 * 2的位置上的6,右孩子是2 * 2 + 1位置上的8

深度优先搜索:

b站up“左程云”,他在经典递归里讲到了, java版本,c/c++/py用户可以听他的思路。
b站up“一只会code的小金鱼”,讲了两个dfs专题,c/c++版本,也讲思路。

思路:

结点不多,如果强行建树,应该也可以,不过巨麻烦。
后序遍历,即“左右根”,最后一个就是根结点,但是只能明显看出来第一个根节点
后续的根节点就只能去判断左子树右子树节点个数,进而判断左右根节点(暴力)
我选择的是递归建树,先往左子树搜索,到底部(没有左子树了)之后,每一次回溯会进入右子树,当右子树到底之后(没有右子树了),将结点存入相应的位置。

AcCode:

#include<bits/stdc++.h>
using namespace std;
int tree[40], back[40], cnt = 1, N;
void dfs(int idx){
    if(idx > N) return ;
    dfs(idx * 2);
    dfs(idx * 2 + 1);
    tree[idx] = back[cnt++];
}

int main(){
    cin >> N;
    for(int i = 1; i <= N; i++){
        cin >> back[i];
    }
    dfs(1);
    for(int i = 1; i <= N; i++){
        cout << tree[i];
        if(i != N) cout << " ";
    }
    return 0;
}
posted @ 2025-03-05 21:58  Yuhhhhh  阅读(223)  评论(0)    收藏  举报