1

题目大意

给定一棵含有N个节点的二叉树,判断是否是完全二叉树

算法思路

判断一颗二叉树是否是完全二叉树的规则:

  • 1、如果出现只有右孩子节点的,一定不是
  • 2、如果出现只有左孩子或者没有孩子节点的,记录该情况
  • 3、如果当前有孩子,并且出现了情况2,一定不是
  • 4、遍历树中所有节点后,如果没有1和3,表明该树为完全二叉树

遍历方式采用层序遍历。在遍历过程中使用count记录遍历的节点个数,在count=N的时候说明来到了最后一个节点,使用lastNode记录。
对于根节点的确定可以使用一个father数组记录每一个节点的父节点编号,初始化全部为-1,在输入结束后,遍历一遍,第一次遇到-1的编号就是根节点。

提交结果

image.png

AC代码

#include <cstdio>
#include <iostream>
#include <queue>

using namespace std;

struct Node{
    int left = -1;
    int right = -1;
    int index{};
}nodes[25];

queue<Node> que;
int lastNode;

bool isComplete(int root,int N){
    que.push(nodes[root]);
    bool flag = false;// 标记是否出现情况2
    int count = 0;
    while(!que.empty()){
        Node t = que.front();
        que.pop();
        ++count;
        if(count==N){
            // 最后一个节点
            lastNode = t.index;
        }
        if(t.left==-1&&t.right!=-1) {
            // 情况1
            return false;
        }else if(t.left!=-1||t.right!=-1) {
            // 当前节点有孩子
            if(flag){
                return false;
            }
        }else if((t.left!=-1&&t.right==-1)||(t.left==-1&&t.right==-1)){
            // 只有左孩子或者没有孩子
            flag = true;
        }
        if(t.left!=-1){
            que.push(nodes[t.left]);
        }
        if(t.right!=-1){
            que.push(nodes[t.right]);
        }
    }
    return true;
}

int main() {
    int N;
    scanf("%d",&N);
    int father[N];
    for(int i=0;i<N;++i){
        father[i] = -1;
    }
    string left,right;
    for(int i=0;i<N;++i){
        cin>>left>>right;
        nodes[i].index = i;
        if(left!="-"){
            int leftChild = stoi(left);
            father[leftChild] = i;
            nodes[i].left = leftChild;
        }
        if(right!="-"){
            int rightChild = stoi(right);
            father[rightChild] = i;
            nodes[i].right = rightChild;
        }
    }
    int root = 0;
    for(int i=0;i<N;++i){
        if(father[i]==-1){
            root = i;
            break;
        }
    }
    if(isComplete(root,N)){
        printf("YES %d",lastNode);
    }else{
        printf("NO %d",root);
    }
    return 0;
}

乔梓鑫
569 声望17 粉丝

主要分享个人学习经验和心得