一颗完全二叉树,求其结点个数

求一颗完全二叉树的结点个数 一颗完全二叉树,要求时间复杂度小于O(n)的,算出这颗树的结点个数 解析 可以利用完全二叉树的性质进行求解,先计算左子树最大的深度,然后利用算出右子树最大深度,如果左子树和右子树最大深度相同,则左子树的结点可以求出(2^n-1);若左子树和右子树最大深度不同,则可以算出右子树的结点;然后依次递归求出右子树或左子树。. public int nodeNum(Node head){ ... 阅读详情

网上看了很多人的答案,都说最优解是o(n),想到了一种更快的算法,复杂度是O(lgn的平方),就是对左右子树进行二分,找最后一层的最右边那个结点即可:


#include <iostream>
#include <cmath>
#include <stdlib.h>

using namespace std;

struct Node {
  Node* left;
  Node* right;
  ~Node() {
    if (left) {
      delete left;
      left = NULL;
    }
    if (right) {
      delete right;
      right = NULL;
    }
  }
};

int GetDepth(Node* root) {
  int depth = 0;
  while (root) {
    depth++;
    root = root->left;
  }
  return depth;
}

void GetMostRightDepthAndIndex(Node* root, int* depth, int* index) {
  while (root) {
    if (root->right) {
      root = root->right;
      *index = (*index - 1) * 2;
      *index += 2;
      *depth += 1;
    } else if (root->left) {
      root = root->left;
      *index = (*index - 1) * 2;
      *index += 1;
      *depth += 1;
    } else {
      return;
    }
  }
}

void GetMostLeftDepthAndIndex(Node* root, int* depth, int* index) {
  while (root) {
    if (root->left) {
      root = root->left;
      *index = (*index - 1) * 2;
      *index += 1;
      *depth += 1;
    }
    else if (root->left) {
      root = root->right;
      *index = (*index - 1) * 2;
      *index += 2;
      *depth += 1;
    } else {
      return;
    }
  }
}

void GetNodeNum(Node* root, int cur_depth, int cur_index,
    int* node_num, int max_depth) {
  if (!root->left) {
    if (cur_depth - 1 >= 1) {
      *node_num += pow(2, cur_depth - 1) - 1;
    }
    *node_num += cur_index;
    return;
  }
  int ml_depth = root->left ? cur_depth + 1 : cur_depth;
  int ml_index = (cur_index - 1) * 2 + 1;
  int mr_depth = root->right ? cur_depth + 1 : cur_depth;
  int mr_index = (cur_index - 1) * 2 + 2;
  GetMostRightDepthAndIndex(root->left, &ml_depth, &ml_index);
  GetMostLeftDepthAndIndex(root->right, &mr_depth, &mr_index);
  if (ml_depth == mr_depth) {
    if (ml_depth == max_depth) {
      GetNodeNum(root->right, cur_depth + 1, (cur_index - 1) * 2 + 2,
          node_num, max_depth);
    } else if (ml_depth < max_depth) {
      GetNodeNum(root->left, cur_depth + 1, (cur_index - 1) * 2 + 1,
          node_num, max_depth);
    } else {
      std::cout << "illegal tree";
      exit(1);
    }
  } else if (ml_depth > mr_depth) {
    if (ml_depth == max_depth && mr_depth == max_depth - 1) {
      *node_num = pow(2, ml_depth - 1) - 1 + ml_index;
    }
  } else {
    std::cout << "illegal tree";
    exit(1);
  }
}

int main() {
  /* Input: create a  */
  // depth 1
  Node* root = new Node();
  // depth 2
  root->left = new Node();
  root->right = new Node();
  // depth 3
  root->left->left = new Node();
  root->left->right = new Node();
  root->right->left = new Node();
  root->right->right = new Node();
  // depth 4
  root->left->left->left = new Node();
  root->left->left->right= new Node();
  root->left->right->left = new Node();
  root->left->right->right = new Node();
  root->right->left->left = new Node();
  root->right->left->right = new Node();
  root->right->right->left = new Node();
  root->right->right->right = new Node();
  // depth 5
  root->left->left->left->left = new Node();

  int root_depth = 1;
  int root_index = 1;
  int max_depth = GetDepth(root);
  int node_num = 0;
  GetNodeNum(root, root_depth, root_index, &node_num, max_depth);
  std::cout << "node_num = " << node_num << endl;
  delete root;
}




从查表法到实时计算:SimpleFOC库中正弦函数优化的技术演进 本文深入探讨了SimpleFOC库v2.0.1版本中正弦函数优化技术的演进,从传统查表法到实时计算的创新实践。通过定点数优化、对称性利用和分段线性插值等关键技术,实现了在嵌入式电机控制中的高效三角函数计算,显著提升性能和资源利用率。 阅读详情

相关推荐

基于STM32的电子时钟设计

基于STM32的电子时钟设计1、设计目的2、设计具体要求3、proteus仿真图4、程序代码 1、设计目的 (1)掌握使用KEIL MDK5进行软件开发的具体流程; (2)掌握硬件电路的设计方法; (3)掌握STM32微控制器的程序设计及代码编写方法。 2、设计具体要求 (1)通过STM32自带的实时时钟功能获取时间信息; (2)在OLED显示屏上显示日期、时、分、秒等时间信息; (3)通过按键可对时间信息进行修改; (4)具有闹钟设定功能; (5)加分项:自行增加其他功能。 3、proteus仿真图 4

唯一的博客 2万+

二叉树11:完全二叉树的节点个数

给你一棵 完全二叉树 的根节点 root ,求出该树的节点个数。 完全二叉树 的定义如下:在完全二叉树中,除了最底层节点可能没填满外,其余每层节点数都达到最大值,并且最下面一层的节点都集中在该层最左边的若干位置。若最底层为第 h 层,则该层包含 1~ 2h 个节点。

Ge_yangwen的博客 2393

手把手教你为ArduPilot添加自定义飞行模式:以自动巡检航线为例

本文详细介绍了如何为开源飞控ArduPilot添加自定义飞行模式,并以自动巡检航线为例,提供了从状态机设计、代码实现到地面站集成的完整开发指南。通过七步法手把手教学,帮助开发者深入理解飞控核心逻辑,实现无人机自主执行复杂巡检任务,满足行业应用定制需求。

weixin_29306875的博客 137

二叉树之求解节点个数类算法归纳

二叉树求解节点个数类一、求二叉树中节点总数二、求二叉树中度为0的节点个数三、求二叉树中度为1的节点个数四、求二叉树中度为2的节点个数五、求二叉树第k层节点个数六、结果展示 以此树为例: 一、求二叉树中节点总数 int getNodeNumRec(BiTree* T) { if (T == NULL) { return 0; } else { return getNodeNumRec(T->lchild) + getNodeNumRec(T->rchild) + 1 ; }

bradyM的博客 5732

Ansys Lumerical 启动时出现 Error: Could not connect to Ansys license server specified at 1055@ 的另一种解决办法

昨天在关闭了中之后 就能正常打开 FDTD 了,结果今天想开启出现了同样的报错:我猜测昨天能启动的原因在于关闭之后要重启电脑,并且在重启之后我第一时间打开 lumerical 测试因此端口没有被占用,今天是在电脑启动之后一段时间才打开所以又遇到了端口占用的问题。

qq_51404184的博客 9549

自动驾驶必备:5分钟搞懂gPTP如何实现μs级时间同步(附开源代码)

本文深入解析了gPTP协议在自动驾驶系统中实现微秒级时间同步的核心机制与工程实践。针对多传感器融合与跨域协同的严苛需求,文章拆解了gPTP的频率同步、对等延迟测量与时间偏移校正三步流程,并提供了基于linuxptp和AVnu gPTP两大开源代码库的实战配置指南与性能评估方法,助力开发者构建高精度、高可靠的车载时间同步网络。

weixin_29211309的博客 167

求二叉树的节点个数

如果是空树,则结点个数为0,递归结束 否则结点个数为左子树的结点个数+右子树的结点个数+1 【算法描述】 int NodeCount(BiTree T) { if (T == NULL) return 0; // 如果是空树,则结点个数为0,递归结束 else return NodeCount(T->lchild) + NodeCount(T->rchild) + 1; //否则结点个数为左子树的结点个数+右子树的结点个数+1 } 具体代

qq_47142993的博客 1万+

告别手动画图!用SUMO的netedit快速搭建高速公路交织区路网(附完整XML文件)

本文详细介绍了如何使用SUMO的netedit工具高效构建高速公路交织区路网,避免手动绘图的低效与错误。通过实战案例和XML文件示例,帮助交通工程专业学生快速掌握复杂道路结构建模技巧,特别解析了spreadType参数设置和速度单位换算等关键操作。

weixin_29085865的博客 261

二叉树——222.完全二叉树的节点个数(递归+迭代)

222. 完全二叉树的节点个数 给你一棵 完全二叉树 的根节点 root ,求出该树的节点个数。 完全二叉树 的定义如下:在完全二叉树中,除了最底层节点可能没填满外,其余每层节点数都达到最大值,并且最下面一层的节点都集中在该层最左边的若干位置。若最底层为第 h 层,则该层包含 1~ 2h 个节点。 提示: 树中节点的数目范围是[0, 5 * 104] 0 <= Node.val <= 5 * 104 题目数据保证输入的树是完全二叉树 解题思路:这个题解题思路可以分为两种...

getinobacar的博客 2505

虚幻商城 Fab 免费资产自动化入库

Fab 商城的所有的免费资产自动化入库

一碗清深的博客 3640

使用 Visual Studio Code 连接 ABAP On-Premise 系统做开发的详细配置步骤

本文详细介绍了如何在Visual Studio Code中通过ABAP Development Tools扩展连接ABAP On-Premise系统。关键步骤包括:通过Ctrl+Shift+P打开命令行面板选择「ABAP: New Destination...」创建RFC连接(仅支持SSO单点登录),选择本地SAPGUI中已有的系统,输入Client ID、语言和用户名(无需密码),最后将目标系统添加到工作区即可开始开发。文章强调了企业安全考虑下仅支持SSO的设计理念,并展示了连接配置的JSON格式示例。整

2007 年 ~ 2025 年,深耕 SAP 技术 18 年 987

完全二叉树的结点数

完全二叉树有一个关于结点数的性质: 结点从1开始编号,层序。那么分每一个结点(编号为i)的左孩子结点是2i,右孩子结点编号是2i+1. 反之,根据孩子结点的编号可以推知父结点的编号:孩子结点编号的一半取整。下面是一个应用的例子: 一棵完全二叉树有1001个结点。其中叶结点的个数是几个? 分析: 1001个结点,则最后一个结点的编号是1001,那么它的父亲结点编号是500,注意,这个并不一

m0_37701448的博客 5541

《SAP FICO系统配置从入门到精通共40篇》030、集成配置:FI与生产计划(PP)的自动科目确定

FI和PP的自动科目确定,本质上是把生产业务翻译成会计语言。翻译规则就藏在那些配置表里。配的时候多想一步:这个业务动作,在财务眼里是什么?是材料消耗?是产出入库?还是工费分摊?想清楚这个,再看配置界面,那些代码就不是天书了。最好的测试方式,是月底关账前,让生产部门跑一遍所有类型的生产订单。配置对不对,业务最知道。

985大学毕业,前某大厂员工,啥都会点的程序员! 574

已知一棵完全二叉树,求其节点的个数

已知一棵完全二叉树,求其节点个数。 要求:时间复杂度低于 O(N),N为这棵树的节点个数 已知,如果一棵满二叉树的高度为l,则它的节点个数为2^l-1 如下的一棵完全二叉树 因为是完全二叉树,所以只要通过遍历它的左边界,就能知道它的层数H,代价为O(logN) 然后遍历头节点右子树的左边界,如果右子树的左边界到了最后一层,说明左子树是满的,所以左树的节点数就能确定,是2^(H-1)-1,再加上头节点,就是2^(H-1)个,剩下右树也是完全二叉树,递归,求右树的节点数。 另一种情况,右子树的左边界没到最

qq_45797026的博客 1517

TMS_WebGMaps_1.9.8.0_Full_Source

TMS_WebGMaps_1.9.8.0_Full_Source 全源码 delphi cbuilder

RU DOS版、EFI版32bit/64bit BIOS常用工具

DOS版、EFI版的RU工具,可用来查看IO、MEM、PCI、SMBIOS等资源。亲测在EFI SHELL下可用。

[2011]若一棵完全二叉树有768个结点,则该二叉树中叶结点的个数是()

一道比较典型的题目

m0_74200587的博客 1413

假人有限元模型

假人模型,车辆碰撞假人有限元模型,适合做乘员安全的研究者利用

【数据结构】二叉树的基本操作大全,学会二叉树基本操作这一篇就够了:二叉树前序、中序、后序、层次遍历;求二叉树总结点个数,叶子结点个数,二叉树第k层的结点个数;求二叉树的高度;在二叉树中查找值为x的结点

【数据结构】二叉树的基本操作大全,学会二叉树基本操作这一篇就够了:二叉树前序、中序、后序、层次遍历;求二叉树总结点个数,叶子结点个数,二叉树第k层的结点个数;求二叉树的高度;在二叉树中查找值为x的结点

2301_76606232的博客 6022

判断一颗二叉树是否是完全二叉树

判断一颗二叉树是否是完全二叉树 方法一,采取标记的方法 非完全二叉树的三种情况 思路分析: 通过层序遍历来遍历树中的每一个非空结点 遍历到的每一个结点都分为四种情况 1.既有左孩子也有右孩子 操作:将左孩子和右孩子入队列 2.只有左孩子 操作: 1.首先判断标记是否处于激活状态,如果标记处于激活状态,直接返回 false 2.满足标记条件,将标记设置为激活状态 3.只有...

吃口雪花的博客 8272

设一棵完全二叉树具有1000个结点,则此完全二叉树有()叶子结点,有()个度为2的结点。

设一棵完全二叉树具有1000个结点,则此完全二叉树有()叶子结点,有()个度为2的结点。

Code_流苏:在代码中寻诗意,在实践中觅真知 4495

已知一颗完全二叉树,求其节点的个数

时间复杂度要求低于0(N),N为这棵树的节点个数 思路: 一颗完全二叉树L他的节点个数是2L-1; 对于一颗满二叉树,顺着他的左子树往下走,我们很快就能知道他的深度以及整棵树节点的大致个数那个区间, 然后在顺着头结点右孩子的左子树不停地走,当在深度那一层有节点的时候,那么整个左子树都是满的,因为我们知道深度那么这个时候左子树的个数就是确定的(2(L-1) - 1),递归去求右子数, 总结一下:整个...

cyyyyyh的博客 1223

已知一颗完全二叉树的第6层(设根为第一层)有8个叶结点,则该完全二叉树的结点个数最多为

已知一颗完全二叉树的第6层(设根为第一层)有8个叶结点,则该完全二叉树的结点个数最多为

weixin_49408416的博客 9242

二叉树详解(求二叉树的结点个数、深度、第k层的个数、遍历等)

对于二叉树,有一种特殊的情况,即一共有k层,前k-2层每个结点的度都是2,第k-1层若有个结点有子树,则其左侧的结点均有子树,这种情况被称为完全二叉树。二叉树,是一种特殊的树,特点是树的度小于等于2(树的度是整个树的结点的度的最大值),由于该特性,构建二叉树的结点只有三个成员,结点的值和指向结点左、右子树的指针。思路:对于每个结点,求左子树的结点的个数和右子树的结点的个数,再加上根节点,就是以当前结点为根的树的结点的个数。4.层序遍历:一层一层的访问,每一层都是先访问左侧的结点再访问右侧的。

yyssas的博客 1517

树与二叉树——二叉树中计算叶子结点个数问题

1、已知完全二叉树具有967个结点,则其叶子结点个数为: 详解: 首先明确一点该二叉树是一棵二叉树,那可以使用二叉树的一些性质。 从第一层开始计算每层的节点个数:1,2,4,8,16,32,64,128,256,512,1024... 将前9层的结点数量全部加起来有511个,如果加上第十层1024,则超过967,所以该完全二叉树肯定是有十层的,所以叶子结点分布在第9层和第10层,且第10层...

fu_jian_ping的博客 1万+

求完全二叉树的结点个数

第一次见这个题,看时间小于O(N)。。。。。 只能是二分啊。 但是怎么二分,条件是什么,真的想不到。   后来知道了,我们要找最深一层最右边那个结点。借此确定结点个数。   我们知道,满二叉树的结点个数和深度是有公式的,那么我们找到最后一层最右边的结点,其实就可以确定结点个数。 目标:找箭头指向的结点。   我们采用二分法: 1)找到右子树的最左结点 如果右子树深...

少说,多做。 7796

满二叉树与完全二叉树

满二叉树与完全二叉树满二叉树定义特点完全二叉树定义特点 满二叉树 定义 在一棵二叉树中,如果所有分支结点都有左、右孩子结点,并且叶子结点都集中在二叉树的最下层,这样的二叉树称为满二叉树。如下图所示就是一棵满二叉树。 用户可以对满二叉树的结点进行层序编号,约定编号从树根为1开始,按照层数从小到大、同一层从左到右的次序进行,图中每个结点旁的数字为对该结点的编号。 满二叉树也可以从结点个数和树的高度之间的关系来定义,即一棵高度为h且有2h-1个结点的二叉树称为满二叉树。 特点 ①、叶子结点都在最下一层 ②、只

muyuxifeng的博客 1万+

完全二叉树的结点个数

完全二叉树的结点个数 思路: 首先通过一直遍历节点的左节点,一直到最左下的结点,这就是二叉树的高度h,之后从根节点的右子树出发,找右子树的最左结点。 1.若右子树的最左结点处在h层上,说明根节点的左子树是一个高度为h-1的满二叉树,结点个数为2^(h-1)-1,之后+1(根节点),递归遍历根节点右子树。 2.若右子树的最左结点不在h层上,说明根节点的右子树是一个高度为h-2的满二叉树,同样上述计算...

amor_1的博客 4292
上一篇: 快速排序的改进算法
下一篇: 按层次打印二叉树元素
bobten2008
博客等级 码龄18年 153粉丝 157原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

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

抵扣说明:

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

余额充值