Java数据结构第十三期:走进二叉树的奇妙世界(二)
专栏:数据结构(Java版)
个人主页:手握风云
目录
一、二叉树的遍历
1.1. 前序遍历
1.2. 中序遍历
1.3. 后序遍历
1.4. 完整代码
二、二叉树的基本操作
2.1. 获取树中结点个数
2.1. 获取叶子结点个数
2.3. 获取第k层结点的个数
2.4. 获取二叉树的高度
2.5. 检测值为value的元素是否存在
一、二叉树的遍历
1.1. 前序遍历
前序遍历又叫先根遍历。每一个节点的遍历顺序都是按照“根——>左子树——>右子树”的顺序来遍历,每遇到一个新的结点都看作是一棵新的树。如果遇到空,则递归回上一个节点。A的右子树遍历过程也如下,所以前序遍历的结果为“ABDCEF”。
1.2. 中序遍历
中序遍历的顺序为“左子树——>根——>右子树”,遇到一个结点,先去遍历左子树,如果该节点的根为空,才能递归回来进行打印。所以中序遍历的结果为“DBAECF”。
1.3. 后序遍历
后序遍历的顺序为“左子树——>右子树——>根”,遍历过程与上面两种都差不多,这里不再多说。后序遍历的顺序为“DBEFCA”。
1.4. 完整代码
public class BinaryTree {static class TreeNode{public char val;public TreeNode left;public TreeNode right;public TreeNode(char val) {this.val = val;}}public TreeNode CreateTree(){TreeNode A = new TreeNode('A');TreeNode B = new TreeNode('B');TreeNode C = new TreeNode('C');TreeNode D = new TreeNode('D');TreeNode E = new TreeNode('E');TreeNode F = new TreeNode('F');A.left = B;A.right = C;B.left = D;C.left = E;C.right = F;return A;}public void PrevOrder(TreeNode root){//前序遍历if(root == null){return;}System.out.print(root.val+" ");PrevOrder(root.left);PrevOrder(root.right);}public void InOrder(TreeNode root){//中序遍历if(root == null){return;}InOrder(root.left);System.out.print(root.val+" ");InOrder(root.right);}public void PostOrder(TreeNode root){//后序遍历if(root == null){return;}PostOrder(root.left);PostOrder(root.right);System.out.print(root.val+" ");}
}
public class Test {public static void main(String[] args) {BinaryTree binaryTree = new BinaryTree();BinaryTree.TreeNode root = binaryTree.CreateTree();System.out.print("前序遍历:");binaryTree.PrevOrder(root);System.out.println();System.out.print("中序遍历:");binaryTree.InOrder(root);System.out.println();System.out.print("后序遍历:");binaryTree.PostOrder(root);}
}
二、二叉树的基本操作
2.1. 获取树中结点个数
我们先回想以下如何获取链表中的结点个数。我们定义一个ListNode cur变量,当cur不为空时,count递增。同样的,我们上面已经实现了二叉树结点的遍历,我们也只需要再定义一个计数器,只要root不为空,countNode就递增。
public void NodeSize(TreeNode root){if(root == null){return;}CountSize++;NodeSize(root.left);NodeSize(root.right);}
上面的是遍历思路,还有一种子问题思路。整棵树的结点个数等于左树的结点数和右树的结点数再加一,只要root为空,那么我们就可以结束递归。
public int NodeSize2(TreeNode root){if(root == null){return 0;}int tmp = NodeSize2(root.left)+NodeSize2(root.right)+1;return tmp;}
2.1. 获取叶子结点个数
叶子结点就是没有左右子树的结点,递推公式为左子树叶子结点加右子树结点,结束条件为结点的左右子树都为空。
//获取叶子结点个数public int getLeafNodeCount(TreeNode root){if(root == null){return 0;}else if(root.left == null && root.right == null){return 1;}else{return getLeafNodeCount(root.left)+ getLeafNodeCount(root.right);}}public int LeafCount;//遍历问题public void getLeafNodeCount2(TreeNode root){if(root == null){return;}if(root.left == null && root.right == null){LeafCount++;}getLeafNodeCount2(root.left);getLeafNodeCount2(root.right);}
2.3. 获取第k层结点的个数
比如我们要想获取第3层结点的个数,就要求root.left第2层和root.right的第二层,相当于左树的第一层和右树的第一层。当k=1时,已经找到这一层,此时也是递归的结束条件。
//获取第k层结点的个数public int getLevelNodeCount(TreeNode root,int k){if(root == null){return 0;}if(k == 1){return 1;}return getLevelNodeCount(root.right,k-1) +getLevelNodeCount(root.left,k-1);}
2.4. 获取二叉树的高度
求二叉树的高度,整棵树的高度等于左子树高度的最大值或者右子树高度的最大值加一,当root为空的时候,高度为0。由于我们不知道是左子树高还是右子树高,所以两边都需要遍历。
//获取二叉树的高度public int getHeight(TreeNode root){if(root == null){return 0;}int leftH = getHeight(root.left);int rightH = getHeight(root.right);return Math.max(leftH,rightH) + 1;}
2.5. 检测值为value的元素是否存在
我们先检查根结点是不是,然后再遍历左子树和右子树,当我们找到了val值,直接返回,不用再递归下面了。
// 检测值为value的元素是否存在public TreeNode find(TreeNode root,int val){if(root == null){return null;}if(root.val == val){return root;}TreeNode leftVal = find(root.left,val);if(leftVal != null){return leftVal;}TreeNode rightVal = find(root.right,val);if(rightVal != null){return rightVal;}return null;}
public class Solution {public static void main(String[] args) {BinaryTree binaryTree = new BinaryTree();BinaryTree.TreeNode root = binaryTree.CreatTree();binaryTree.NodeSize(root);System.out.println("结点个数:"+binaryTree.CountSize);System.out.println("结点个数:"+binaryTree.NodeSize2(root));System.out.println("叶子结点个数:"+binaryTree.getLeafNodeCount(root));binaryTree.getLeafNodeCount2(root);System.out.println("叶子结点个数:"+binaryTree.LeafCount);System.out.println("第3层结点个数:"+binaryTree.getLevelNodeCount(root,3));System.out.println("二叉树的高度:"+binaryTree.getHeight(root));}
}
相关文章:

Java数据结构第十三期:走进二叉树的奇妙世界(二)
专栏:数据结构(Java版) 个人主页:手握风云 目录 一、二叉树的遍历 1.1. 前序遍历 1.2. 中序遍历 1.3. 后序遍历 1.4. 完整代码 二、二叉树的基本操作 2.1. 获取树中结点个数 2.1. 获取叶子结点个数 2.3. 获取第k层结点的个数 2.4. 获取二叉树的…...
JavaScript系列(86)--现代构建工具详解
JavaScript 现代构建工具详解 🔨 现代前端开发离不开构建工具,它们帮助我们处理模块打包、代码转换、资源优化等任务。让我们深入了解主流的构建工具及其应用。 构建工具概述 🌟 💡 小知识:构建工具主要解决代码转换…...

docker容器网络配置及常用操作
Linux内核实现名称空间的创建 ip netns(网络名称空间)命令 可以借助ip netns命令来完成对 Network Namespace 的各种操作。ip netns命令来自于iproute安装包,一般系统会默认安装,如果没有的话,请自行安装。 注意&am…...
Docker 性能优化指南
Docker 提供了强大的容器化功能,能够帮助开发者在不同的环境中构建、测试和部署应用。然而,随着容器化应用的不断增长,Docker 容器可能会面临一些性能瓶颈,影响其运行效率、资源占用和扩展能力。为了确保容器在生产环境中的高效运…...

课程1. 深度学习简介
课程1. 深度学习简介 神经网络结构逻辑回归XOR问题(异或问题) 中间特征的生成全连接神经网络中间网络层的激活函数Sigmoid函数Tanh函数ReLU函数其它激活函数 使用全连接神经网络解决 XOR 问题神经网络用于回归问题训练神经网络 不同类型的神经网络 附加材…...

【cuda学习日记】4.3 结构体数组与数组结构体
4.3 数组结构体(AoS)和结构体数组(SoA) AoS方法进行存储 struct innerStruct{float x;float y; };struct innerStruct myAOS[N];SoA方法来存储数据 struct innerArray{float x[N];float y[N]; };struct innerArray moa;如图说明…...

2025最新高维多目标优化:基于城市场景下无人机三维路径规划的导航变量的多目标粒子群优化算法(NMOPSO),MATLAB代码
一、基于导航变量的多目标粒子群优化算法(NMOPSO)介绍 基于导航变量的多目标粒子群优化算法(Navigation variable-based multi-objective particle swarm optimization,NMOPSO)是2025年提出的一种用于无人机路径规划的…...

数字IC后端设计实现OCC(On-chip Clock Controller)电路介绍及时钟树综合案例
数字IC后端时钟树综合专题(OCC电路案例分享) 复杂时钟设计时钟树综合(clock tree synthesis)常见20个典型案例 1、什么是OCC? 片上时钟控制器(On-chip Clock Controllers ,OCC),也称为扫描时钟控制器(Scan Clock Con…...

Linux内核,slub分配流程
我们根据上面的流程图,依次看下slub是如何分配的 首先从kmem_cache_cpu中分配,如果没有则从kmem_cache_cpu的partial链表分配,如果还没有则从kmem_cache_node中分配,如果kmem_cache_node中也没有,则需要向伙伴系统申请…...

本地部署DeepSeek-R1(Ollama+Docker+OpenWebUI知识库)
安装Ollama 打开 Ollama官网 https://ollama.com/下载安装 Ollama服务默认只允许本机访问,修改允许其它主机访问 OLLAMA_HOST0.0.0.0 ollama serve也可以添加系统环境变量 都知道模型体积很大,顺便也通过环境变量修改模型存放位置,我这…...
Java 实现快速排序算法:一条快速通道,分而治之
大家好,今天我们来聊聊快速排序(QuickSort)算法,这个经典的排序算法被广泛应用于各种需要高效排序的场景。作为一种分治法(Divide and Conquer)算法,快速排序的效率在平均情况下非常高ÿ…...

20250223下载并制作RTX2080Ti显卡的显存的测试工具mats
20250223下载并制作RTX2080Ti显卡的显存的测试工具mats 2025/2/23 23:23 缘起:我使用X99的主板,使用二手的RTX2080Ti显卡【显存22GB版本,准备学习AI的】 但是半年后发现看大码率的视频容易花屏,最初以为是WIN10经常更换显卡/来回更…...

element-ui的组件使用
1. 安装 Element UI(在文件夹最上面输入cmd进入dos窗口,然后输入安装指令 npm install element-ui --save) 2.在main.js文件全局引入(main.js文件负责 全局注册 ),在该文件注册的所有组件在其他文件都能直接调用,一般…...

医疗AI领域中GPU集群训练的关键技术与实践经验探究(上)
医疗AI领域中GPU集群训练的关键技术与实践经验探究(上) 一、引言 1.1 研究背景与意义 在科技飞速发展的当下,医疗 AI 作为人工智能技术与医疗领域深度融合的产物,正引领着医疗行业的深刻变革。近年来,医疗 AI 在疾病诊断、药物研发、健康管理等诸多方面取得了显著进展,…...
详解Redis淘汰策略
引言 Redis 是一个高性能的内存数据库,广泛应用于缓存系统、消息队列等场景。当 Redis 的内存达到限制时,需要根据一定的策略来淘汰数据,以便腾出空间给新数据。本文将深入解析 Redis 的内存淘汰机制,帮助更好地配置 Redis&#…...

HarmonyOS 5.0应用开发——鸿蒙接入高德地图实现POI搜索
【高心星出品】 文章目录 鸿蒙接入高德地图实现POI搜索运行结果:准备地图编写ArkUI布局来加载HTML地图 鸿蒙接入高德地图实现POI搜索 在当今数字化时代,地图应用已成为移动设备中不可或缺的一部分。随着鸿蒙系统的日益普及,如何在鸿蒙应用中…...

nginx关于配置SSL后启动失败原因分析
在配置SSL后,启动./nginx失败,报错提示如下: nginx: [emerg] the "ssl" parameter requires ngx_http_ssl_module in /usr/local/nginx-1.27.4/conf/nginx.conf:36 这个错误提示表在配置nginx启用SSL时,nginx未启用 ng…...

【自学嵌入式(9)ESP8266网络服务器的使用】
ESP8266网络服务器的使用 ESP8266WiFi 库① WiFiClass② WiFiClient③ WiFiServer④ WiFiUDP ESP8266WiFiMulti 库① WiFiMulti ESP8266WebServer 库① ESP8266WebServer 网络服务器实例在浏览器中控制ESP8266指示灯将开发板引脚状态显示在网页中 在之前的文章中,曾…...

危化品经营单位安全管理人员的职责及注意事项
危化品经营单位安全管理人员肩负着保障经营活动安全的重要责任,以下是其主要职责及注意事项: 职责 1. 安全制度建设与执行:负责组织制定本单位安全生产规章制度、操作规程和生产安全事故应急救援预案,确保这些制度符合国家相关法…...
项目实战--网页五子棋(匹配模块)(5)
上期我们实现了websocket后端的大部分代码,这期我们实现具体的匹配逻辑 1. 定义Mather类 我们新建一个Matcher类用来实现匹配逻辑 Component public class Matcher {//每个匹配队列代表不同的段位,这里约定每一千分为一个段位private ArrayList<Queue<User…...
后进先出(LIFO)详解
LIFO 是 Last In, First Out 的缩写,中文译为后进先出。这是一种数据结构的工作原则,类似于一摞盘子或一叠书本: 最后放进去的元素最先出来 -想象往筒状容器里放盘子: (1)你放进的最后一个盘子(…...
FFmpeg 低延迟同屏方案
引言 在实时互动需求激增的当下,无论是在线教育中的师生同屏演示、远程办公的屏幕共享协作,还是游戏直播的画面实时传输,低延迟同屏已成为保障用户体验的核心指标。FFmpeg 作为一款功能强大的多媒体框架,凭借其灵活的编解码、数据…...
前端倒计时误差!
提示:记录工作中遇到的需求及解决办法 文章目录 前言一、误差从何而来?二、五大解决方案1. 动态校准法(基础版)2. Web Worker 计时3. 服务器时间同步4. Performance API 高精度计时5. 页面可见性API优化三、生产环境最佳实践四、终极解决方案架构前言 前几天听说公司某个项…...

Opencv中的addweighted函数
一.addweighted函数作用 addweighted()是OpenCV库中用于图像处理的函数,主要功能是将两个输入图像(尺寸和类型相同)按照指定的权重进行加权叠加(图像融合),并添加一个标量值&#x…...

【第二十一章 SDIO接口(SDIO)】
第二十一章 SDIO接口 目录 第二十一章 SDIO接口(SDIO) 1 SDIO 主要功能 2 SDIO 总线拓扑 3 SDIO 功能描述 3.1 SDIO 适配器 3.2 SDIOAHB 接口 4 卡功能描述 4.1 卡识别模式 4.2 卡复位 4.3 操作电压范围确认 4.4 卡识别过程 4.5 写数据块 4.6 读数据块 4.7 数据流…...

2.Vue编写一个app
1.src中重要的组成 1.1main.ts // 引入createApp用于创建应用 import { createApp } from "vue"; // 引用App根组件 import App from ./App.vue;createApp(App).mount(#app)1.2 App.vue 其中要写三种标签 <template> <!--html--> </template>…...
质量体系的重要
质量体系是为确保产品、服务或过程质量满足规定要求,由相互关联的要素构成的有机整体。其核心内容可归纳为以下五个方面: 🏛️ 一、组织架构与职责 质量体系明确组织内各部门、岗位的职责与权限,形成层级清晰的管理网络…...
【C语言练习】080. 使用C语言实现简单的数据库操作
080. 使用C语言实现简单的数据库操作 080. 使用C语言实现简单的数据库操作使用原生APIODBC接口第三方库ORM框架文件模拟1. 安装SQLite2. 示例代码:使用SQLite创建数据库、表和插入数据3. 编译和运行4. 示例运行输出:5. 注意事项6. 总结080. 使用C语言实现简单的数据库操作 在…...

涂鸦T5AI手搓语音、emoji、otto机器人从入门到实战
“🤖手搓TuyaAI语音指令 😍秒变表情包大师,让萌系Otto机器人🔥玩出智能新花样!开整!” 🤖 Otto机器人 → 直接点明主体 手搓TuyaAI语音 → 强调 自主编程/自定义 语音控制(TuyaAI…...
什么?连接服务器也能可视化显示界面?:基于X11 Forwarding + CentOS + MobaXterm实战指南
文章目录 什么是X11?环境准备实战步骤1️⃣ 服务器端配置(CentOS)2️⃣ 客户端配置(MobaXterm)3️⃣ 验证X11 Forwarding4️⃣ 运行自定义GUI程序(Python示例)5️⃣ 成功效果![在这里插入图片描述](https://i-blog.csdnimg.cn/direct/55aefaea8a9f477e86d065227851fe3d.pn…...