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

105.【C语言】数据结构之二叉树求总节点和第K层节点的个数

目录

1.求二叉树总的节点的个数

1.容易想到的方法

代码

缺陷

思考:能否在TreeSize函数内定义静态变量解决size的问题呢?

其他写法

运行结果

2.最好的方法:分而治之

代码

运行结果

2.求二叉树第K层节点的个数

错误代码

运行结果

修正

运行结果

其他写法


1.求二叉树总的节点的个数

1.容易想到的方法

借助103.【C语言】数据结构之二叉树的三种递归遍历方式文章的遍历函数的思想

以前序遍历函数的思想为例

void PreOrder(BTNode* root)
{//先判断是否为空树(叶节点的左节点和右节点均为空树)if (root == NULL){printf("NULL ");return;}//按根-->左子树-->右子树的顺序遍历printf("%d ",root->data);PreOrder(root->left);PreOrder(root->right);
}

设计TreeSize函数,设size存储二叉树的总的节点的个数,由于局部变量在函数返回时会发生销毁,显然应该使用全局变量size,在main函数外部写int size;(默认初始值为0)

代码

#include "Tree.h"
int size;
void TreeSize(BTNode* root)
{if (root == NULL)//为NULL,则返回,不+1{return;}size++;//根节点+1TreeSize(root->left);TreeSize(root->right);
}int main()
{BTNode* root = CreateTree();TreeSize(root);printf("TreeSize==%d", size);return 0;
} 

备注:CreateTree建立的是下面这棵二叉树

c1b93c8d50e7492e8f0316990818f57a.png
 

递归的思想和103.【C语言】数据结构之二叉树的三种递归遍历方式文章相同,不再赘述

运行结果

1810fb1a01884fa6b5c0e72fb6fd1746.png

缺陷

本方法有缺陷,当多次调用时必须手动为size置0

若像下面这样不置0


int main()
{BTNode* root = CreateTree();TreeSize(root);printf("TreeSize==%d\n", size);TreeSize(root);printf("TreeSize==%d\n", size);TreeSize(root);printf("TreeSize==%d\n", size);return 0;
} 

运行结果会出错

1788d73414a940f0ace0dd190a7efa12.png

每一次调用前必须手动置0,像下面这样


int main()
{BTNode* root = CreateTree();TreeSize(root);printf("TreeSize==%d\n", size);size = 0;TreeSize(root);printf("TreeSize==%d\n", size);size = 0;TreeSize(root);printf("TreeSize==%d\n", size);return 0;
} 

思考:能否在TreeSize函数内定义静态变量解决size的问题呢?

答:不可以,理由1:无论函数调用多少次,写在函数内的静态变量只会被初始化一次,即第二,三,四,...次调用不会初始化.理由2:在函数外部无法访问静态变量

其他写法

TreeSize多传一个参数

#include "Tree.h"
void TreeSize(BTNode* root,int* psize)
{if (root == NULL)//为NULL,则返回,不+1{return;}(*psize)++;//根节点+1TreeSize(root->left, psize);TreeSize(root->right, psize);
}int main()
{BTNode* root = CreateTree();int size1 = 0;TreeSize(root, &size1);printf("TreeSize==%d\n", size1);int size2 = 0;TreeSize(root, &size2);printf("TreeSize==%d\n", size2);int size3 = 0;TreeSize(root, &size3);printf("TreeSize==%d\n", size3);return 0;
}
运行结果

3412e19c2ded489b9672f6cef3a9fbb2.png

2.最好的方法:分而治之

形象说法:找"下属"分担任务(递归),让"下属"帮忙计数,"下属"统计好个数交给"上司"(此方法不用定义size)

递推:根将任务交给左子树和右子树,左子树和右子树将任务分别交给它们的左子树和右子树,左子树和右子树将任务分别交给它们的左子树和右子树...一直到空树结束

代码

int TreeSize(BTNode* root)
{if (root == NULL){return 0;}return TreeSize(root->left) + 1 + TreeSize(root->right);//+1加的是自己本身
}int main()
{BTNode* root = CreateTree();printf("TreeSize=%d\n", TreeSize(root));printf("TreeSize=%d\n", TreeSize(root));printf("TreeSize=%d\n", TreeSize(root));return 0;
}

运行结果

可见无论TreeSize被执行多少次,打印的结果都是一样的,从而避免了要将size置为0的问题

2.求二叉树第K层节点的个数

分析:比如求下图K=3层的节点个数,按递归思想分析

递推:关键点:要以不同的视角来看待第K层

求K层-->求根节点的左右子树的第K-1层-->求根节点的左右子树的第K-2层-->...-->求根节点的左右子树的第1层

由上述分析可知TreeLevel函数需要BTNode* root和int k两个参数,这里k必须大于0(assert(k>0);)

错误代码

int TreeLevel(BTNode* root, int k)
{assert(k>0);if (root == NULL){return 0;}int lnum = TreeLevel(root->left, k - 1);int rnum = TreeLevel(root->right, k - 1);return lnum + rnum;
}int main()
{BTNode* root = CreateTree();printf("TreeLevel=%d", TreeLevel(root, 3));return 0;
}
运行结果

运行结果显然是有问题的,怎么修正?

修正

错误原因:考虑其一没有考虑其二,if判断处一直返回0,没有返回1的情况,导致0+0+...+0==0

    if (root == NULL){return 0;}

TreeLevel返回有两种情况:1.根节点为NULL 2.k==1

修改后

int TreeLevel(BTNode* root, int k)
{assert(k>0);if (root == NULL){return 0;}if (k == 1){return 1;}int lnum = TreeLevel(root->left, k - 1);int rnum = TreeLevel(root->right, k - 1);return lnum + rnum;
}
运行结果

结果正确

其他写法

不用变量存储,直接返回相加的值

int TreeLevel(BTNode* root, int k)
{assert(k>0);if (root == NULL){return 0;}if (k == 1){return 1;}return TreeLevel(root->left, k - 1) + TreeLevel(root->right, k - 1);
}

相关文章:

105.【C语言】数据结构之二叉树求总节点和第K层节点的个数

目录 1.求二叉树总的节点的个数 1.容易想到的方法 代码 缺陷 思考:能否在TreeSize函数内定义静态变量解决size的问题呢? 其他写法 运行结果 2.最好的方法:分而治之 代码 运行结果 2.求二叉树第K层节点的个数 错误代码 运行结果 修正 运行结果 其他写法 1.求二…...

力扣637. 二叉树的层平均值

给定一个非空二叉树的根节点 root , 以数组的形式返回每一层节点的平均值。与实际答案相差 10-5 以内的答案可以被接受。 提示&#xff1a; 树中节点数量在 [1, 104] 范围内-231 < Node.val < 231 - 1 代码&#xff1a; /*** Definition for a binary tree node.* stru…...

【前端】Next.js 服务器端渲染(SSR)与客户端渲染(CSR)的最佳实践

关于Next.js 服务器端渲染&#xff08;SSR&#xff09;与客户端渲染&#xff08;CSR&#xff09;的实践内容方面&#xff0c;我们按下面几点进行阐述。 1. 原理 服务器端渲染 (SSR): 在服务器上生成完整的HTML页面&#xff0c;然后发送给客户端。这使得用户在首次访问时能够…...

路径规划之启发式算法之一:A-Star(A*)算法

A*算法是一种启发式搜索算法&#xff0c;常用于解决路径规划问题。 一、A*算法的定义与原理 A*算法是一种用于在图形或网格中查找最短路径的算法。它在搜索过程中综合考虑了每个节点的实际距离&#xff08;g值&#xff09;和预估距离&#xff08;h值&#xff09;&#xff0c;以…...

Android复习代码1-4章

public class RudioButton extends AppCompatActivity {Overrideprotected void onCreate(Nullable Bundle savedInstanceState) {super.onCreate(savedInstanceState);setContentView(R.layout.activity_rudio_button);// 找到RadioGroup和TextView的实例RadioGroup radioGrou…...

【问题】webdriver.Chrome()设置参数executable_path报不存在

场景1: 标红报错unresolved reference executable_path 场景2: 执行报错TypeError: __init__() got an unexpected keyword argument executable_path 原因&#xff1a; 上述两种场景是因为selenium4开始不再支持某些初始化参数。比如executable_path 解决&#xff1a; 方案…...

win10系统安装docker-desktop

1、开启Hyper-v ———————————————— Hyper-V 是微软提供的一种虚拟化技术&#xff0c;它允许你在同一台物理计算机上运行多个独立的操作系统实例。这种技术主要用于开发、测试、以及服务器虚拟化等领域。 —————————————————————— &#…...

小程序-基于java+SpringBoot+Vue的乡村研学旅行平台设计与实现

项目运行 1.运行环境&#xff1a;最好是java jdk 1.8&#xff0c;我们在这个平台上运行的。其他版本理论上也可以。 2.IDE环境&#xff1a;IDEA&#xff0c;Eclipse,Myeclipse都可以。推荐IDEA; 3.tomcat环境&#xff1a;Tomcat 7.x,8.x,9.x版本均可 4.硬件环境&#xff1a…...

组件A底部栏(position: fixed )事件使用$emit更新内容失败bug解决

今天遇到一个很离奇的bug&#xff0c;记录一下 问题&#xff1a;在组件内底部栏使用$emit触发按钮事件但打印出来的值是初始化的值&#xff0c;更新的值被重置导致更新失败 原因&#xff1a;组件内底部使用了 position: fixed; 固定&#xff0c; 导致组件内插槽 this 与 保存按…...

数据结构——排序第三幕(深究快排(非递归实现)、快排的优化、内省排序,排序总结)超详细!!!!

文章目录 前言一、非递归实现快排二、快排的优化版本三、内省排序四、排序算法复杂度以及稳定性的分析总结 前言 继上一篇博客基于递归的方式学习了快速排序和归并排序 今天我们来深究快速排序&#xff0c;使用栈的数据结构非递归实现快排&#xff0c;优化快排&#xff08;三路…...

C++的类功能整合

1. 类的基本概念 类是面向对象编程的核心&#xff0c;它封装了数据和操作数据的函数。 #include <iostream> using namespace std;class MyClass { public:int publicData;void publicFunction() {cout << "Public function" << endl;}private:i…...

《String类》

目录 一、定义与概述 二、创建字符串对象 2.1 直接赋值 2.2 使用构造函数 三、字符串的不可变性 四、常用方法 4.1 String对象的比较 4.1.1 比较是否引用同一个对象 4.1.2 boolean equals(Object anObject)方法&#xff1a;按照字典序比较 4.1.3 int compareTo(Strin…...

【docker】docker的起源与容器的由来、docker容器的隔离机制

Docker 的起源与容器的由来 1. 虚拟机的局限&#xff1a;容器的需求萌芽 在 Docker 出现之前&#xff0c;开发和部署软件主要依赖虚拟机&#xff08;VMs&#xff09;&#xff1a; 虚拟机通过模拟硬件运行操作系统&#xff0c;每个应用程序可以运行在自己的独立环境中。虽然虚…...

Window 安装 Nginx

参考链接 Windows 环境nginx安装使用及目录结构详解_windows 安装nginx-CSDN博客 Nginx 安装及配置教程&#xff08;Windows&#xff09;【安装】_nginx下载安装-CSDN博客 安装 1&#xff09;下载 nginx: download 2&#xff09;解压 3&#xff09;启动 3.1&#xff09;方…...

replace (regexp|substr, newSubstr|function)替换字符串中的指定部分

replace 方法用于替换字符串中的指定部分。它可以接受一个子字符串或正则表达式作为第一个参数&#xff0c;第二个参数是替换的内容。 用法示例 基本替换 let str "Hello, world!"; let newStr str.replace("world", "everyone"); console.lo…...

【ROS2】Ubuntu22.04安装ROS humble

一. ROS简介 1.1 什么是ROS ROS 是一个适用于机器人的开源的元操作系统。它提供了操作系统应有的服务&#xff0c;包括硬件抽象&#xff0c;底层设备控制&#xff0c;常用函数的实现&#xff0c;进程间消息传递&#xff0c;以及包管理。ROS的核心思想就是将机器人的软件功能做…...

cesium 3Dtiles变量

原本有一个变亮的属性luminanceAtZenith&#xff0c;但是新版本的cesium没有这个属性了。于是 let lightColor 3.0result._customShader new this.ffCesium.Cesium.CustomShader({fragmentShaderText:void fragmentMain(FragmentInput fsInput, inout czm_modelMaterial mate…...

配置泛微e9后端开发环境

配置泛微e9的后端开发环境 1.安装jdk1.8&#xff08;请自行安装并设置环境变量&#xff09; 2.将服务器上的WEARVER文件夹拷贝到开发环境下(其中要包含ecology和Resin目录) 3.通过idea创建一个基础Java项目,将jdk设置为1.8 4.添加依赖,需要将3个文件夹的所有jar包添加到项目中…...

【Stable Diffusion】安装教程

目录 一、python 安装教程 二、windows cuda安装教程 三、Stable Diffusion下载 四、Stable Diffusion部署&#xff08;重点&#xff09; 一、python 安装教程 &#xff08;1&#xff09;第一步下载 打开python下载页面&#xff0c;找到python3.10.9&#xff0c;点击右边…...

USB Type-C一线通扩展屏:多场景应用,重塑高效办公与极致娱乐体验

在追求高效与便捷的时代&#xff0c;启明智显USB Type-C一线通扩展屏方案正以其独特的优势&#xff0c;成为众多职场人士、娱乐爱好者和游戏玩家的首选。这款扩展屏不仅具备卓越的性能和广泛的兼容性&#xff0c;更能在多个应用场景中发挥出其独特的价值。 USB2.0显卡&#xff…...

Terraform状态锁定与Terratest:并发测试解决方案

Terraform状态锁定与Terratest&#xff1a;并发测试解决方案 【免费下载链接】terratest Terratest is a Go library that makes it easier to write automated tests for your infrastructure code. 项目地址: https://gitcode.com/gh_mirrors/te/terratest 在现代Dev…...

SOONet多场景落地:司法审讯录像关键陈述定位、医疗手术步骤索引

SOONet多场景落地&#xff1a;司法审讯录像关键陈述定位、医疗手术步骤索引 1. 项目概述 SOONet是一个基于自然语言输入的长视频时序片段定位系统&#xff0c;它能够通过一次网络前向计算就精确定位视频中的相关片段。这个技术解决了传统视频分析中需要逐帧查看或依赖复杂算法…...

Cogito-V1-Preview-Llama-3B LSTM时间序列预测模型原理与代码实现详解

Cogito-V1-Preview-Llama-3B LSTM时间序列预测模型原理与代码实现详解 1. 引言 时间序列预测&#xff0c;简单来说&#xff0c;就是根据过去的数据&#xff0c;猜一猜未来会发生什么。这事儿听起来挺玄乎&#xff0c;但其实我们每天都在做。比如&#xff0c;看看天气预报&…...

Docker Compose一键部署JupyterHub:20人团队协作环境搭建实录(含中文支持)

Docker Compose实战&#xff1a;20人团队JupyterHub协作环境搭建全指南 去年我们数据科学团队扩容到18人时&#xff0c;共享笔记本服务器频繁崩溃的问题突然爆发。每次周会前半小时&#xff0c;总有同事在群里喊"服务器又卡死了"&#xff0c;直到我们用Docker Compos…...

硬件密码引擎(CE)技术解析:嵌入式安全加速核心

1. 硬件密码引擎&#xff08;CE&#xff09;模块技术解析 1.1 模块定位与工程价值 硬件密码引擎&#xff08;Crypto Engine&#xff0c;简称 CE&#xff09;并非通用计算单元&#xff0c;而是面向嵌入式系统安全需求深度定制的专用协处理器。其核心价值在于将原本由主控 CPU 承…...

APK-Installer:轻量级Windows APK安装工具解决跨平台应用运行难题

APK-Installer&#xff1a;轻量级Windows APK安装工具解决跨平台应用运行难题 【免费下载链接】APK-Installer An Android Application Installer for Windows 项目地址: https://gitcode.com/GitHub_Trending/ap/APK-Installer APK-Installer是一款专为Windows系统设计…...

Phi-3-vision-128k-instruct与低代码平台集成:在Dify中构建视觉AI应用

Phi-3-vision-128k-instruct与低代码平台集成&#xff1a;在Dify中构建视觉AI应用 1. 引言&#xff1a;当视觉大模型遇上低代码 想象一下&#xff0c;你是一家电商公司的运营人员&#xff0c;每天需要处理上千张商品图片——识别商品类别、提取关键属性、生成营销文案。传统方…...

GLM-OCR与ComfyUI工作流集成:可视化构建智能图文处理管线

GLM-OCR与ComfyUI工作流集成&#xff1a;可视化构建智能图文处理管线 你是不是也遇到过这样的场景&#xff1f;看到一张特别有感觉的图片&#xff0c;想模仿它的风格生成一张新的&#xff0c;却不知道该怎么描述那种色调和构图。或者&#xff0c;手头有一堆产品图&#xff0c;…...

Kafka(二):从Lambda到Kappa,流批一体计算的起源

你好&#xff0c;我是程序员贵哥。 在上节课里&#xff0c;我们已经了解了Kafka的基本架构。不过&#xff0c;对于基于Kafka的流式数据处理&#xff0c;我们还有两个重要的问题没有回答&#xff1a; 第一个&#xff0c;Kafka的分布式是如何实现的呢&#xff1f;我们已经看到了K…...

人工智能时代算力基建哪家强?

中国联通与中国电信&#xff1a;人工智能、云计算、无人驾驶与机器人通信的竞争优势分析 ——基于2025-2026年券商研报与行业动态的深度解读 摘要 在“十五五”规划开局之年&#xff08;2026年&#xff09;&#xff0c;中国通信行业正经历从“传统管道商”向“数字智能服务商”…...