【C++搜索二叉树】

文章目录

    • 二叉搜索树
      • 二叉搜索树的概念
      • 二叉搜索树的操作
      • 搜索二叉树的具体实现

二叉搜索树

二叉搜索树的概念

二叉搜索树又称二叉排序树,它或者是一棵空树,或者是具有以下性质的二叉树:

  • 若它的左子树不为空,则左子树上所有节点的值都小于根节点的值
  • 若它的右子树不为空,则右子树上所有节点的值都大于根节点的值
  • 它的左右子树也分别为二叉搜索树
    在这里插入图片描述

二叉搜索树的操作

  1. 二叉搜索树的查找
    a、从根开始比较,比根大走右边,比根小走左边
    b、如果走到到空,还没找到,这个值不存在

  2. 二叉搜索树的插入
    插入的具体过程如下:
    a. 树为空,则直接新增节点,赋值给root指针
    b. 树不空,按二叉搜索树性质查找插入位置,插入新节点

  3. 二叉搜索树的删除
    首先查找是否在二叉搜索树中,如果不存在则返回,如果存在,则分三种情况:
    情况a:如果该节点只有左孩子节点,删除该结点且使被删除节点的双亲结点指向被删除节点的左孩子结点–直接删除
    情况b:如果该节点只有右孩子节点,删除该结点且使被删除节点的双亲结点指向被删除结点的右孩子结点–直接删除
    情况c:如果该节点右左,右孩子节点,在它的右子树中寻找中序下的第一个结点(,用它的值填补到被删除节点中,再来处理该结点的删除问题–替换法删除

搜索二叉树的具体实现

	template<class K>struct BSTNode{typedef BSTNode<K> Node;Node* _left;Node* _right;K _key;BSTNode(const K& key):_left(nullptr),_right(nullptr),_key(key){}};template<class K>class BSTree{typedef BSTNode<K> Node;public:BSTree() = default;BSTree(const BSTree<K>& t){_root = _Copy(t._root);}BSTree<int> operator=(BSTree<K> t){swap(_root, t._root);return *this;}~BSTree(){_Destroy(_root);_root = nullptr;}bool Find(const K& key){Node* curr = _root;while (curr){if (curr->_key > key)curr = curr->_left;else if (curr->_key < key)curr = curr->_right;elsereturn true;}return false;}bool Insert(const K& key){if (_root == nullptr){_root = new Node(key);return true;}Node* parent = nullptr;Node* curr = _root;while (curr){if (curr->_key > key){parent = curr;curr = curr->_left;}else if (curr->_key < key){parent = curr;curr = curr->_right;}elsereturn false;}Node* newnode = new Node(key);if (parent->_key < key)parent->_right = newnode;elseparent->_left = newnode;return true;}bool Erase(const K& key){Node* parent = nullptr;Node* curr = _root;while (curr){if (curr->_key > key){parent = curr;curr = curr->_left;}else if (curr->_key < key){parent = curr;curr = curr->_right;}else	{//找到了//左子树为空if (curr->_left == nullptr){//如果找到了这个节点且父亲为空,那么这个节点一定是rootif (parent == nullptr){delete _root;_root = nullptr;}else{if (parent->_left == curr)parent->_left = curr->_right;elseparent->_right = curr->_right;delete curr;}}//右子树为空else if (curr->_right == nullptr){//同上if (parent == nullptr){delete _root;_root = nullptr;}else{if (parent->_left == curr)parent->_left = curr->_left;elseparent->_right = curr->_left;delete curr;}}//两颗子树都不为空else{Node* minParent = curr;Node* minNode = curr->_right;while (minNode->_left){minParent = minNode;minNode = minNode->_left;}swap(curr->_key, minNode->_key);if (minParent->_left == minNode)minParent->_left = minNode->_right;elseminParent->_right = minNode->_right;delete minNode;}return true;}}return false;}void InOrder(){_InOrder(_root);cout << '\n';}bool FindR(const K& key){return _FindR(_root, key);}bool InsertR(const K& key){return _InsertR(_root, key);}bool EraseR(const K& key){return _EraseR(_root, key);}private:bool _EraseR(Node*& root, const K& key){if (root == nullptr)return false;if (root->_key < key)return _EraseR(root->_right, key);else if (root->_key > key)return _EraseR(root->_left, key);else{//找到了if (root->_left == nullptr){if (root == _root){delete _root;_root = nullptr;}else{root = root->_right;}}else if (root->_right == nullptr){if (root == _root){delete _root;_root = nullptr;}else{root = root->_left;}}else{Node* minParent = root;Node* minNode = root->_right;while (minNode->_left){minParent = minNode;minNode = minNode->_left;}swap(root->_key, minNode->_key);return _EraseR(root->_right, key);}return true;}}//因为传的是引用,所以root是上一栈帧中root的左/右节点指针的别名//修改root,就是修改上一栈帧中root的左右节点指针bool _InsertR(Node*& root, const K& key){if (root == nullptr){root = new Node(key);return true;}if (root->_key < key)return _InsertR(root->_right, key);else if (root->_key > key)return _InsertR(root->_left, key);elsereturn false;}bool _FindR(Node* root, const K& key){if (root == nullptr)return false;if (root->_key > key)return _FindR(root->_left, key);else if (root->_key < key)return _FindR(root->_right, key);elsereturn true;}void _Destroy(Node* root){if (root == nullptr)return;_Destroy(root->_left);_Destroy(root->_right);delete root;}Node* _Copy(Node* root){if (root == nullptr) return nullptr;Node* newnode = new Node(root->_key);newnode->_left = _Copy(root->_left);newnode->_right = _Copy(root->_right);return newnode;}void _InOrder(Node* root){if (root == nullptr)return;_InOrder(root->_left);cout << root->_key << ' ';_InOrder(root->_right);}Node* _root = nullptr;};

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/455568.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【安卓跨程序共享数据,探究ContentProvider】

ContentProvider主要用于在不同的应用程序之间实现数据共享的功能&#xff0c;它提供了一套完整的机制&#xff0c;允许一个程序访问另一个程序中的数据&#xff0c;同时还能保证被访问数据的安全性。 目前&#xff0c;使用ContentProvider是Android实现跨程序共享数据的标准方…

【机器学习与自然语言处理】预训练 Pre-Training 各种经典方法的概念汇总

【NLP概念合集&#xff1a;一】预训练 Pre-Training&#xff0c;微调 Fine-Tuning 及其方法的概念区别 前言请看此正文预训练 Pre-Training无监督学习 unsupervised learning概念&#xff1a;标签PCA 主成分分析&#xff08;Principal Component Analysis&#xff09;降维算法L…

Web课程学习笔记--CSS-Sprite的应用

雪碧图CSS Sprite的应用 CSS雪碧&#xff0c;即CSS Sprite&#xff0c;也有人叫它CSS精灵&#xff0c;是一种CSS图像合并技术&#xff0c;该方法是将小图标和背景图像合并到一张图片上&#xff0c;然后利用css的背景定位来显示需要显示的图片部分。例如常见的商品分类导航其实所…

代码手术刀-自定义你的代码重构工具

前言 笔者近日在做代码仓库的存量代码缩减工作&#xff0c;首先考虑的是基于静态扫描的缩减&#xff0c;尝试使用了很多工具来对代码进行优化&#xff0c;例如PMD、IDEA自带的inspect功能、findBugs等。但是无一例外&#xff0c;要么过于“保守”&#xff0c;只给出扫描结果&a…

分享springboot框架的一个开源的本地开发部署教程(若依开源项目开发部署过程分享持续更新二开宝藏项目PostgresSQL数据库版)

1首先介绍下若依项目&#xff1a; 若依是一个基于Spring Boot和Spring Cloud技术栈开发的多租户权限管理系统。该开源项目提供了一套完整的权限管理解决方案&#xff0c;包括用户管理、角色管理、菜单管理、部门管理、岗位管理等功能。 若依项目采用前后端分离的架构&#xf…

基于OpenCV灰度图像转GCode的单向扫描实现

基于OpenCV灰度图像转GCode的单向扫描实现 引言单向扫描存在的问题灰度图像单向扫描代码示例结论 系列文章 ⭐深入理解G0和G1指令&#xff1a;C中的实现与激光雕刻应用⭐基于二值化图像转GCode的单向扫描实现⭐基于二值化图像转GCode的双向扫描实现⭐基于二值化图像转GCode的…

青马在线考试怎么搜题找答案?不妨看看这九个实用工具 #知识分享#微信#笔记

在信息爆炸的时代&#xff0c;选择适合自己的学习辅助工具和资料&#xff0c;能够提供更高效、便捷和多样化的学习方式。 1.WolframAlpha WolframAlpha堪称“数学解题神器”&#xff01; 可以搜索到大学多个专业的题目以及试卷答案&#xff0c;重点是提供的题目搜索大部分的…

第二代Qwen大模型发布,阿里巴巴一口气开源了30个不同参数规模的模型

关于Qwen-1.5系列更多信息参考DataLearnerAI原文&#xff1a; 重磅&#xff01;第二代通义千问大模型开源&#xff0c;阿里巴巴一口气开源了30个不同参数规模的模型&#xff0c;其中Qwen1.5-72B仅次于GPT-4.​www.datalearner.com/blog/1051707149237037​编辑https://link.zh…

性能实测:分布式存储 ZBS 与集中式存储 HDS 在 Oracle 数据库场景表现如何

作者&#xff1a;深耕行业的 SmartX 金融团队 金鑫 在金融客户的基础架构环境中&#xff0c;HDS 是一种被广泛使用的存储解决方案。作为集中式存储的代表之一&#xff0c;HDS 拥有高性能、高可用性和可扩展性的企业级存储特点&#xff0c;适用于实时数据处理、虚拟化和灾难备份…

Docker下安装GitLab

极狐GitLab Docker 镜像 | 极狐GitLab 安装所需最小配置 内存至少4G 系统内核至少3.10以上 uname -r 命令可以查看系统内核版本 安装Docker 1.更新 yum源 yum update 2.安装依赖(如果在操作第三步的时候提示yum-config-manager 未找到命令 就安装下面依赖) yum instal…

杨中科 ASP.NETCORE 高级14 SignalR

1、什么是websocket、SignalR 服务器向客户端发送数据 1、需求&#xff1a;Web聊天;站内沟通。 2、传统HTTP&#xff1a;只能客户端主动发送请求 3、传统方案&#xff1a;长轮询&#xff08;Long Polling&#xff09;。缺点是&#xff1f;&#xff08;1.客户端发送请求后&…

防范恶意勒索攻击!亚信安全发布《勒索家族和勒索事件监控报告》

本周态势快速感知 本周全球共监测到勒索事件81起&#xff0c;事件数量有所下降&#xff0c;比上月降低20%。 lockbit3.0仍然是影响最严重的勒索家族&#xff1b;akira和incransom也是两个活动频繁的恶意家族&#xff0c;需要注意防范。 本周alphv勒索组织窃取MBC法律专业公司…