数据结构之判断一棵树是不是完全二叉树

简介: 数据结构之判断一棵树是不是完全二叉树

1 完全二叉树

完全二叉树是由 满二叉树 而引出来的。对于深度为K的,有n个结点的二叉树,当且仅当其每一个结点都与深度为K的满二叉树中编号从1至n的结点一一对应时称之为完全二叉树。

如下就是完全二叉树

                1
      2                    3
4           5        6           7


如下就是完全二叉树

                1
      2                    3
4           5       


如下不是完全二叉树

                1
      2                    3
4           5                    7

2 分析

判断一颗二叉树是不是完全二叉树,我们用层遍历数(这里需要用到队列)


1)如果根节点为NULL, 返回false,不是的话,我们queue把根节点push到里面去,然后在放到queue大小不为空的循环里面,进行queue.front()操作得到节点。


2)如果节点的左叶子是空,右叶子节点不是空,直接返回false。


3)如果节点的左叶子不是空,右叶子节点不是空,我们分别把左右叶子节点压去queue,同时pop出最前面的元素。


4)如果遇到一个结点,左叶子不为空,右叶子为空;或者左右叶子都为空;则该节点之后的队列中的结点都为叶子节点;该树才是完全二叉树,否则就不是完全二叉树


3 代码实现

#include <iostream>
#include <queue>
using namespace std;
typedef struct Tree 
{
    int value;
    struct Tree* left;
    struct Tree* right;
    Tree(int value):value(value), left(NULL), right(NULL){}
} Tree;
bool isCompleteTree(Tree* node)
{
    if (node == NULL)
        return false;
    queue<Tree *> queue;
    queue.push(node);
    while (!queue.empty())
    {
        Tree *pNode = queue.front();
        //左叶子是空,右叶子节点不是空
        if (pNode->left == NULL && pNode->right != NULL)
            return false;
        //左叶子不是是空,右叶子节点不是空
        if (pNode->left != NULL && pNode->right != NULL)
        {
            queue.pop();
            queue.push(pNode->left);
            queue.push(pNode->right);
        }
        //左叶子不为空,右叶子为空;或者左右叶子都为空;则该节点之后的队列中的结点都为叶子节点;该树才是完全二叉树,否则就不是完全二叉树
        if ((pNode->left == NULL && pNode->right == NULL) || (pNode->left != NULL && pNode->right == NULL))
        {
            if (pNode->left != NULL && pNode->right == NULL)
            {
                queue.push(pNode->left);
            }
            queue.pop();
            while (!queue.empty())
            {
                Tree* node = queue.front();
                if (node->left == NULL && node->right == NULL)
                {
                    queue.pop();
                }
                else
                {
                    std::cout << "false...." << std::endl;
                    return false;
                }        
            }
            return true;
        }
    }
    return true;
}
int main()
{
    Tree node1(1);
    Tree node2(2);
    Tree node3(3);
    Tree node4(4);
    Tree node5(5);
    Tree node6(6);
    Tree node7(7);
    node1.left = &node2;
    node1.right = &node3;
    node2.left = &node4;
    node2.right = &node5;
    node3.left = &node6;
    node3.right = &node7;
    std::string res = "";
    res = (isCompleteTree(&node1) == 1) ? "true" : "false";
    std::cout << "Tree isFullTree is " << res << std::endl;
    return 0;
}

4 运行结果

Tree isFullTree is true


5 总结

完全二叉树如果遇到一个结点,左叶子不为空,右叶子为空;或者左右叶子都为空;则该节点之后的队列中的结点都为叶子节点;该树才是完全二叉树,否则就不是完全二叉树


完全二叉树还有这个性质,比如这个树有n个节点,那么这个树的有左右孩子节点的父节点有n / 2个,如果我们堆顶是从下标0开始的,那么n / 2个数就对于于下标0~ (n / 2 - 1),而且如果当前节点是下标i的话(有左右子节点情况),那么它的左孩子节点的下标是2*i + 1,右孩子节点下标是2 * i + 2, 如果我们堆顶是从下标1开始的,那么n / 2个数就对于于下标0~ (n / 2),而且如果当前节点是下标i的话(有左右子节点情况),那么它的左孩子节点的下标是2*i ,右孩子节点下标是2 * i + 1,  

 

相关文章
|
2月前
|
算法
数据结构之博弈树搜索(深度优先搜索)
本文介绍了使用深度优先搜索(DFS)算法在二叉树中执行遍历及构建链表的过程。首先定义了二叉树节点`TreeNode`和链表节点`ListNode`的结构体。通过递归函数`dfs`实现了二叉树的深度优先遍历,按预序(根、左、右)输出节点值。接着,通过`buildLinkedList`函数根据DFS遍历的顺序构建了一个单链表,展示了如何将树结构转换为线性结构。最后,讨论了此算法的优点,如实现简单和内存效率高,同时也指出了潜在的内存管理问题,并分析了算法的时间复杂度。
58 0
|
3月前
|
存储 算法 搜索推荐
探索常见数据结构:数组、链表、栈、队列、树和图
探索常见数据结构:数组、链表、栈、队列、树和图
128 64
|
2月前
|
存储 缓存 算法
在C语言中,数据结构是构建高效程序的基石。本文探讨了数组、链表、栈、队列、树和图等常见数据结构的特点、应用及实现方式
在C语言中,数据结构是构建高效程序的基石。本文探讨了数组、链表、栈、队列、树和图等常见数据结构的特点、应用及实现方式,强调了合理选择数据结构的重要性,并通过案例分析展示了其在实际项目中的应用,旨在帮助读者提升编程能力。
72 5
|
2月前
|
存储 搜索推荐 算法
【数据结构】树型结构详解 + 堆的实现(c语言)(附源码)
本文介绍了树和二叉树的基本概念及结构,重点讲解了堆这一重要的数据结构。堆是一种特殊的完全二叉树,常用于实现优先队列和高效的排序算法(如堆排序)。文章详细描述了堆的性质、存储方式及其实现方法,包括插入、删除和取堆顶数据等操作的具体实现。通过这些内容,读者可以全面了解堆的原理和应用。
109 16
|
2月前
|
算法
数据结构之文件系统模拟(树数据结构)
本文介绍了文件系统模拟及其核心概念,包括树状数据结构、节点结构、文件系统类和相关操作。通过构建虚拟环境,模拟文件的创建、删除、移动、搜索等操作,展示了文件系统的基本功能和性能。代码示例演示了这些操作的具体实现,包括文件和目录的创建、移动和删除。文章还讨论了该算法的优势和局限性,如灵活性高但节点移除效率低等问题。
66 0
|
3月前
|
存储 算法 关系型数据库
数据结构与算法学习二一:多路查找树、二叉树与B树、2-3树、B+树、B*树。(本章为了解基本知识即可,不做代码学习)
这篇文章主要介绍了多路查找树的基本概念,包括二叉树的局限性、多叉树的优化、B树及其变体(如2-3树、B+树、B*树)的特点和应用,旨在帮助读者理解这些数据结构在文件系统和数据库系统中的重要性和效率。
33 0
数据结构与算法学习二一:多路查找树、二叉树与B树、2-3树、B+树、B*树。(本章为了解基本知识即可,不做代码学习)
|
3月前
|
存储 编译器 C++
【初阶数据结构】掌握二叉树遍历技巧与信息求解:深入解析四种遍历方法及树的结构与统计分析
【初阶数据结构】掌握二叉树遍历技巧与信息求解:深入解析四种遍历方法及树的结构与统计分析
|
3月前
【高阶数据结构】二叉树进阶探秘:AVL树的平衡机制与实现详解(三)
【高阶数据结构】二叉树进阶探秘:AVL树的平衡机制与实现详解
|
3月前
【高阶数据结构】二叉树进阶探秘:AVL树的平衡机制与实现详解(二)
【高阶数据结构】二叉树进阶探秘:AVL树的平衡机制与实现详解
|
3月前
|
存储
【高阶数据结构】二叉树进阶探秘:AVL树的平衡机制与实现详解(一)
【高阶数据结构】二叉树进阶探秘:AVL树的平衡机制与实现详解