当前位置: 首页 > article >正文

C++算法练习-day32——222.完全二叉树的节点个数

题目来源:. - 力扣(LeetCode)

题目思路分析

给定一棵二叉树,我们的目标是计算其节点总数。直接遍历所有节点并计数的方法虽然简单,但在最坏情况下(树完全不平衡)的时间复杂度为O(n),其中n是节点总数。为了优化这个计算过程,我们可以利用二叉树的性质。特别是,如果一棵二叉树的左子树和右子树深度相同,那么这棵树就是一个满二叉树(或完全二叉树的一个子集),其节点总数可以直接通过数学公式计算得出。如果左右子树深度不同,我们则分别递归计算左右子树的节点数,然后求和并加上根节点。

代码:

/**  
 * Definition for a binary tree node.  
 * struct TreeNode {  
 *     int val;  
 *     TreeNode *left;  
 *     TreeNode *right;  
 *     TreeNode() : val(0), left(nullptr), right(nullptr) {}  
 *     TreeNode(int x) : val(x), left(nullptr), right(nullptr) {}  
 *     TreeNode(int x, TreeNode *left, TreeNode *right) : val(x), left(left), right(right) {}  
 * };  
 */  
class Solution {  
public:  
    int countNodes(TreeNode* root) {  
        // 如果当前节点为空,则返回0,表示没有节点  
        if(!root){  
            return 0;  
        }  
          
        // 初始化左子树和右子树的深度为0  
        int l_depth = 0, r_depth = 0;  
          
        // 计算左子树的深度  
        TreeNode* node = root;  
        while(node->left){  
            ++l_depth;  
            node = node->left;  
        }  
          
        // 重置node到根节点,计算右子树的深度  
        node = root;  
        while(node->right){  
            ++r_depth;  
            node = node->right;  
        }  
          
        // 如果左子树和右子树的深度相同,说明当前树是满二叉树  
        // 使用公式2^(深度+1) - 1计算满二叉树的节点总数  
        if(l_depth == r_depth){  
            return pow(2, l_depth + 1) - 1;  
        }  
        else{  
            // 如果左右子树深度不同,则分别递归计算左右子树的节点数  
            // 然后将这两个值相加,并加上当前节点(root),得到整棵树的节点总数  
            return countNodes(root->left) + countNodes(root->right) + 1;  
        }  
    }  
};
注释详解
  • if(!root){return 0;}:如果当前节点为空,则返回0,表示没有节点。
  • int l_depth = 0, r_depth = 0;:初始化左子树和右子树的深度为0。
  • TreeNode* node = root;:临时节点,用于遍历子树以计算深度。
  • while(node->left){...}:计算左子树的深度。
  • node = root;:重置临时节点到根节点,用于计算右子树的深度。
  • while(node->right){...}:计算右子树的深度。
  • if(l_depth == r_depth){...}:如果左右子树深度相同,计算满二叉树的节点总数。
  • else{...}:如果左右子树深度不同,递归计算左右子树的节点数并求和。

知识点摘要

  • 二叉树的基本概念:二叉树是一种树形数据结构,其中每个节点最多有两个子节点,称为左子节点和右子节点。
  • 满二叉树:一棵二叉树,如果除了叶子节点外的每个节点都有两个子节点,则称为满二叉树。
  • 递归:递归是一种在函数内部调用函数自身的编程技巧,常用于解决可以分解为相似子问题的问题。
  • 深度优先搜索(DFS):深度优先搜索是一种用于遍历或搜索树或图的算法,它尽可能深地搜索树的分支。

在本文中,我们介绍了一种高效计算二叉树节点总数的方法。通过判断左右子树的深度是否相同,我们可以确定当前树是否为满二叉树,并直接计算其节点总数。如果左右子树深度不同,则递归计算左右子树的节点数并求和。这种方法结合了数学计算和递归,相比直接遍历所有节点的方法,能够显著提高计算效率。通过本文的学习,读者可以掌握这种优化技巧,并在实际编程中加以应用。


http://www.kler.cn/a/378801.html

相关文章:

  • 【点云学习笔记】——分割任务学习
  • Spring框架的事务管理
  • 读数据工程之道:设计和构建健壮的数据系统28数据服务常见关注点
  • 3105. 最长的严格递增或递减子数组
  • Windows的MySQL开机自动启动问题
  • Python小白学习教程从入门到入坑------第二十三课 封装(语法进阶)
  • 宠物排泄物图像分割系统:高效目标识别
  • 开放式耳机什么品牌质量好?5款排行榜里的开放式蓝牙耳机
  • rnn/lstm 项目实战
  • 关于使用K8s实现容器化作业的总时效最优调度
  • 【设计模式】结构型模式(一):适配器模式、装饰器模式
  • 爬虫技术——小白入狱案例
  • “灵境·石景山杯”数字文旅创新大赛晋级名单
  • 路由策略与路由控制
  • CNN-Attention分类预测 | Matlab实现多特征分类预测
  • qt QBrush详解
  • R 语言科研配色 --- 第 9 期
  • 基于SSM的在线作业管理系统 -octopus-master(源码+调试)
  • Go语言有哪些数据类型?
  • Java集合使用注意事项总结
  • 数据结构之二叉树--前序,中序,后序详解(含源码)
  • oracle如何在不同业务场景下正确使用聚合查询、联合查询及分组查询?
  • 使用Java实现机器学习:一个入门指南
  • JS中DOM和BOM
  • Linux常用基本指令和shell
  • RK3568平台开发系列讲解(内存篇)Linux 内存优化