数据结构:二叉搜索树(排序树)
1.二叉搜索树的定义
二叉搜索树要么是空树,要么是满足以下特性的树
(1)左子树不为空,那么左子树左右节点的值都小于根节点的值
(2)右子树不为空,那么右子树左右节点的值都大于根节点的值
(3)其所有子树也满足二叉搜索树性质
(4)二叉搜索树有两种形态,一种是支持插入冗余值,一种是不支持的(一般默认不支持冗余)
简单来说就是左边节点值 < 根节点值 < 右边节点值
二叉搜索树又叫二叉排序树,这是因为如果对他进行中序遍历,将会得到一组升序排序的数据
2.二叉搜索树的性能
二叉搜索树的搜索次数是等于树的高度的
最优情况:对于类似完全二叉树的树结构,时间复杂度可以达到O(logn)
最差情况:对于几乎所有数据都单侧分布的情况,时间复杂度会到O(n)
为了使他保持最优的性能,我们后续会引入平衡的概念,使他保持左右子树高度差小于等于1
3.部分实现非冗余二叉搜索树
节点基本结构搭建:
对于bstree的搭建:只需要加一个private的根节点指针即可
3.1插入
(1)若树为空,则直接新建节点,然后把新节点的地址给bs树的根节点,返回true,表示插入成功
(2)若树不为空,则判断key和当前节点的值的大小
若key小于当前节点的值:往左边搜索
若大于当前节点的值:往右边搜索
若等于当前节点值:直接返回false
如果我只用一个cur指针,是不能完成节点的链接的,因为链接节点的是cur的直接根节点,也就是prvcur节点,所以这里我们才创建一个prvnode指针,就是用于把新节点和bs树进行连接的。
(3)找到之后判断key于待链接节点的值的大小决定插入在左侧还是右侧
接下来进入测试阶段,不过在测试之前我们需要写一个中序遍历的方法,以便更直观的检查逻辑是否正确
我们利用递归的方式实现,结束条件是节点为空。
由于二叉搜索树左子树 < 根节点 < 右子树的性质,我们使用中序遍历可以实现升序输出
不过这里有个问题,我们需要传递bstree的private变量,可以使用友元,实现get函数等方法去获取m_root,现在我们介绍一个新的方式
封装进类中
我们在_inorder中实现具体功能,然后封装到inorder中,inorder主要用于调用m_root给_inorder传递参数
3.2查找
由于我们在插入部分已经进行过查找数据,所以我们只需要对insert的代码稍微改一下即可
下面我们进行调试
对1的查找成功,对11的查找失败,符合预期
3.3删除
对于删除,总共有四种情况
情况1:delete节点为叶子节点
解决方法:找到该节点后让他的父节点指向nullptr,并释放该节点空间
情况2:delete节点只有左节点
解决方法:让他的父节点指向他的那一侧指向delete的左节点
情况3:delete节点只有右节点
解决方法:让他的父节点指向他的那一侧指向delete的右节点
情况4:delete节点左右节点均有
![]()
解决方法:寻找delete左子树的最大节点,或者delete右子树的最小节点,然后交换delete位置的值与replace节点的值,让replace的父节点空余的一侧指向replace节点的左侧(从左子树找时),或者右侧(从右子树找时)。最后释放replace位置的空间
疑问一:为什么是寻找delete左子树的最大节点,或者delete右子树的最小节点?
答:
因为我们需要保持二叉搜索树的排序结构,只能从左树找一个最大数据(保证替换后根大于左树,且由于是从左树找的数据,必然也是小于右树的数据的),或者从右数找一个最小数据(和左树同理)
疑问二:寻找到的replace节点为什么可以直接让其父节点接入另一侧?
答:
因为replace已经是最左或者最右节点,所以不可能两侧都有节点,最多只有另一侧有节点。
特殊情况分析:
(1)对于delete节点有左右节点,且replace的节点就是左子树根节点,或右子树根节点
我们需要把replace的父节点设置为cur,而不是空,否则会有空指针访问。
并且replace父节点的指向侧也不是确定的,这种情况下和会更新replace父节点的情况,父节点的指向侧是相反的
(2)对于delete节点只有右节点或左节点,且delete节点为搜索树的根节点
由于这种基于情况1,2,3的情况下,我们需要释放delete节点的空间,所以根节点需要删除就涉及根节点的指针指向变更。
我们对cur==m_root的情况用if语句单独处理,让m_root指向cur->left或cur->right
代码实现:
(1)大框架搭建:我们使用insert的代码作为查找大框架
我们的代码写在找到delete节点cur的位置
(2)对情况1-3进行处理,并把特殊情况1纳入考虑
由于右侧为空/左侧为空的情况可以兼容两侧为空的情况,所以我们不用单独处理两侧为空的情况
(1)cur左为空
对于cur左为空且cur为根节点:更改m_root,指向cur有节点的一侧,也就是右侧
对于cur非根节点的情况:让父节点指向cur的那一侧指向cur有节点的一侧
(2)cur右为空
(3)cur左右非空
我们实现的是从左子树中查找最大节点,也可以换成从右子树查找最小节点
第一步:
查找replace节点:循环更改replace与replaceprv指针,直到replace指向的节点右侧为空
第二步:
交换delete与replace节点的值
第三步:让replace父节点指向replace节点的左侧
注意:
若replace父节点就是cur,说明节点就在cur的左侧,用父节点左侧指向replace节点左侧。
若replace父节点不为cur,说明进入了循环,而replace父节点就是上一次的replace,replace一直在往右走,所以其父节点一定是右侧指向replace节点
相关文章:
数据结构:二叉搜索树(排序树)
1.二叉搜索树的定义 二叉搜索树要么是空树,要么是满足以下特性的树 (1)左子树不为空,那么左子树左右节点的值都小于根节点的值 (2)右子树不为空,那么右子树左右节点的值都大于根节点的值 &#…...
【愚公系列】《Python网络爬虫从入门到精通》036-DataFrame日期数据处理
标题详情作者简介愚公搬代码头衔华为云特约编辑,华为云云享专家,华为开发者专家,华为产品云测专家,CSDN博客专家,CSDN商业化专家,阿里云专家博主,阿里云签约作者,腾讯云优秀博主,腾讯云内容共创官,掘金优秀博主,亚马逊技领云博主,51CTO博客专家等。近期荣誉2022年度…...
C++(蓝桥杯常考点)
前言:这个是针对于蓝桥杯竞赛常考的C内容,容器这些等下棋期再讲 C 在DEVC中注释和取消注释的方法:ctrl/ ASCII值(常用的): A-Z:65-90 a-z:97-122 0-9:48-57 换行/n:10科学计数法:eg:…...
支付宝 IoT 设备入门宝典(下)设备经营篇
上篇介绍了支付宝 IoT 设备管理,但除了这些基础功能外,商户还可以利用设备进行一些运营动作,让设备更好的帮助自己,本篇就会以设备经营为中心,介绍常见的设备相关能力和问题解决方案。如果对上篇感兴趣,可以…...
蓝桥杯 之 填空题-位运算与循环
文章目录 循环握手问题门牌制作-循环小球反弹幸运数艺术与篮球跑步卡片 位运算3个1美丽的2024 位运算 可以关注这个Lowbit(x) 如何判断最低位是否是1? num&1 1就说明num最低位是1 循环 循环 握手问题 握手问题 思路分析: 可以直接计算出来&…...
iOS逆向工程概述与学习路线图
iOS逆向工程概述与学习路线图 欢迎各位加入我的iOS逆向工程专栏!在这个系列的第一篇文章中,我将为大家介绍iOS逆向工程的基本概念、应用场景以及完整的学习路线图,帮助大家建立清晰的学习框架。 什么是iOS逆向工程? 逆向工程&a…...
DeepSeek 助力 Vue3 开发:打造丝滑的时间选择器(Time Picker)
前言:哈喽,大家好,今天给大家分享一篇文章!并提供具体代码帮助大家深入理解,彻底掌握!创作不易,如果能帮助到大家或者给大家一些灵感和启发,欢迎收藏+关注哦 💕 目录 DeepSeek 助力 Vue3 开发:打造丝滑的时间选择器(Time Picker)📚前言📚页面效果📚指令输入…...
基于 Ingress-Nginx 实现 mTLS 双向认证
目录 背景描述: TLS 和 MTLS 之间的差异 通过自签名证书启用双向 TLS 1. 生成证书 (1) 生成 CA(根证书颁发机构) (2) 生成 CA(根证书颁发机构) (3) 生成客户端证书 2. 在 Kubernetes 中配置 mTLS &#x…...
学到什么记什么(25.3.3)
Upload-labs 今日重新做了一下文件上传漏洞,这里第一题之前采用直接抓包改后缀名.jpg为.php,再写入一句话<?php phpinfo();?>然后放行,得到图片地址(可复制),本来直接访问图片地址即可得到敏感信息…...
【子网掩码计算器:Python + Tkinter 实现】
子网掩码计算器:Python Tkinter 实现 引言代码功能概述代码实现思路1. 界面设计2. 功能实现3. 事件处理 子网掩码计算器实现步骤1. 导入必要的库2. 定义主窗口类 SubnetCalculatorApp3. 创建菜单栏4. 创建界面组件5. 判断 IP 地址类别6. 计算子网信息7. 其他功能函…...
《解锁HarmonyOS NEXT高阶玩法:艺术图像识别功能开发全攻略》
在当今数字化时代,AI技术不断拓展其应用边界,为各行业带来前所未有的变革。在艺术领域,AI图像识别技术能够帮助艺术从业者、爱好者快速识别艺术品风格、作者,甚至挖掘艺术品背后的历史文化信息。本文将结合HarmonyOS NEXT API 12及…...
Spring Boot的启动流程
Spring Boot 的启动流程是一个复杂且有序的过程: 创建SpringApplication实例 — 调用run方法 — 启动完成(发布应用启动事件,配置环境,创建ApplicationContext,准备ApplicationContext,刷新ApplicationContext[【创建B…...
【通俗讲解电子电路】——从零开始理解生活中的电路(三)
实际应用案例:生活中的电子电路 ——拆解你身边的“隐形工程师” 1. 手电筒电路:最简单的直流系统 电路组成 电源:2节1.5V电池(串联3V)。 开关:按钮控制回路通断。 LED:发光二极管ÿ…...
TypeScript系列01-类型系统全解析
本文总结了 TypeScript 的类型系统基础,涵盖了: TypeScript 的价值:静态类型检查为 JavaScript 添加了类型安全保障基本类型系统:从原始类型到特殊类型(any、unknown、never)的完整介绍类型注解与推断&…...
ragflow-mysql 启动失败案例分析
一、问题描述 1.拉取RAGflow镜像失败 dependency failed to start: container ragflow-mysql is unhealthy2. 查询日志 docker logs ragflow-mysql显示 出现[rootlocalhost docker]# docker logs ragflow-mysql Fatal glibc error: CPU does not support x86-64-v2 Fatal …...
SslConnection::SslConnection()详解
一、🔍 SslConnection::SslConnection() 详解 这个构造函数的主要作用是: 创建 SSL 对象创建 BIO(I/O 缓冲区)初始化 SSL 服务器模式绑定回调函数(onRead() 处理接收数据) 📌 1. 初始化 SSL 相…...
unity lua属性绑定刷新
我们现在有一个 角色属性类叫heroModel,内容如下,当heroModel中的等级发生变化的时候,我们需要刷新界面显示等级信息,通常我们是在收到等级升级成功的协议的时候,发送一个事件,UI界面接受到这个事件的时候,刷新一下等级…...
Self-Pro: A Self-Prompt and Tuning Framework for Graph Neural Networks
Self-Pro: A Self-Prompt and Tuning Framework for Graph Neural Networks #paper/GFM/GNN-BASED# #paper/⭐⭐⭐# 注意:这篇文章是每个图一个GCN模型,而不是所有图一个GCN 模型 算是最早的涉及异配图的prompt了 贡献和动机: 非对…...
企业级-数据分类分级详细方案
一、方案背景 在数字化时代,数据成为企业和组织的核心资产。随着数据量的快速增长和数据应用场景的不断拓展,如何有效地管理和保护数据,确保数据的安全性、合规性和可用性,成为了亟待解决的问题。数据分类分级作为数据管理的基础工作,能够帮助企业清晰地了解自身的数据资…...
本地部署Qwen2.5-VL-7B-Instruct模型
本地部署Qwen2.5-VL-7B-Instruct模型 本地部署Permalink **创建环境** conda create -n qwenvl python3.11 -y# 报错: Solving environment: failedPackagesNotFoundError: The following packages are not available from current channels:# 处理: c…...
Guohua Diffusion 创意编程:用Processing可视化交互控制图像生成
Guohua Diffusion 创意编程:用Processing可视化交互控制图像生成 你有没有想过,自己随手画的一条线、选择的一个颜色,能立刻变成一幅由AI生成的完整画作?这听起来像是科幻电影里的场景,但现在,通过一点创意…...
颠覆原神体验:Snap Hutao智能助手如何重构你的游戏效率
颠覆原神体验:Snap Hutao智能助手如何重构你的游戏效率 【免费下载链接】Snap.Hutao 实用的开源多功能原神工具箱 🧰 / Multifunctional Open-Source Genshin Impact Toolkit 🧰 项目地址: https://gitcode.com/GitHub_Trending/sn/Snap.Hu…...
YOLO12入门必看:从上传图片到JSON结果输出完整操作流程
YOLO12入门必看:从上传图片到JSON结果输出完整操作流程 1. 引言:为什么你需要了解YOLO12? 如果你正在寻找一个既快又准的目标检测工具,那么YOLO12的出现,可能就是你一直在等的那个答案。 想象一下这样的场景&#x…...
PDF-Parser-1.0行业报告:市场分析与技术趋势
PDF-Parser-1.0行业报告:市场分析与技术趋势 1. 引言 每天都有成千上万份行业报告、白皮书和研究文档以PDF格式在企业间流转。这些文档蕴含着宝贵的市场洞察、技术趋势和商业机会,但手动提取和分析这些信息需要耗费大量时间和精力。PDF-Parser-1.0的出…...
Qwen2-VL-2B-Instruct一键部署教程:基于Ubuntu 20.04的GPU环境快速搭建
Qwen2-VL-2B-Instruct一键部署教程:基于Ubuntu 20.04的GPU环境快速搭建 你是不是也遇到过这种情况?看到一个很酷的多模态大模型,想立刻上手试试,结果被复杂的依赖安装、环境配置、驱动适配搞得头大,折腾半天还没跑起来…...
深入理解SAP RAP中的语义依赖:从/DMO测试数据看BTP应用的数据建模精髓
解密SAP RAP语义依赖:从/DMO测试数据到企业级数据建模实战 在SAP BTP应用开发领域,数据建模的质量直接决定了系统的健壮性和可维护性。当我们在/DMO/CONNECTION表开发中遇到"DISTANCE字段具有单位量转换和EDM类型int32"的元数据错误时…...
京东抢购自动化全攻略:从入门到精通的技术实践指南
京东抢购自动化全攻略:从入门到精通的技术实践指南 【免费下载链接】JDspyder 京东预约&抢购脚本,可以自定义商品链接 项目地址: https://gitcode.com/gh_mirrors/jd/JDspyder 30秒快速评估:你是否需要JDspyder? 在决…...
革新性Koikatu体验增强工具:KK-HF_Patch效率提升指南
革新性Koikatu体验增强工具:KK-HF_Patch效率提升指南 【免费下载链接】KK-HF_Patch Automatically translate, uncensor and update Koikatu! and Koikatsu Party! 项目地址: https://gitcode.com/gh_mirrors/kk/KK-HF_Patch 你是否曾在《Koikatu》游戏中遇到…...
Cassandra在大数据图像存储中的应用探索
Cassandra在大数据图像存储中的应用探索关键词:Cassandra、大数据、图像存储、分布式系统、数据管理摘要:本文旨在深入探索Cassandra在大数据图像存储领域的应用。我们将先介绍Cassandra的基本概念和特点,再详细分析它与大数据图像存储的适配…...
开源工具SMUDebugTool:系统优化与性能调优的终极解决方案
开源工具SMUDebugTool:系统优化与性能调优的终极解决方案 【免费下载链接】SMUDebugTool A dedicated tool to help write/read various parameters of Ryzen-based systems, such as manual overclock, SMU, PCI, CPUID, MSR and Power Table. 项目地址: https:/…...
















