东莞网站建设管理什么网站从做系统

pingmian/2026/1/24 21:20:53/文章来源:
东莞网站建设管理,什么网站从做系统,亚马逊做外贸英文网站,高中生做那个的网站二叉查找树(BST) 二叉树的一种应用就是来实现堆#xff0c;今天我们再看看用二叉查找树(Binary Search Tree, BST)。 前面有章节说到了查找操作#xff0c;包括线性查找、二分查找、哈希查找等#xff0c;线性查找效率比较低#xff0c;二分又要求必须是有序的序列#x…二叉查找树(BST) 二叉树的一种应用就是来实现堆今天我们再看看用二叉查找树(Binary Search Tree, BST)。 前面有章节说到了查找操作包括线性查找、二分查找、哈希查找等线性查找效率比较低二分又要求必须是有序的序列 为了维持有序插入的代价比较高、哈希查找效率很高但是浪费空间。能不能有一种插入和查找都比较快的数据结构呢二叉查找树就是这样一种结构可以高效地插入和查询节点。 BST 定义 二叉查找树是这样一种二叉树结构它的每个节点包含一个 key 和它附带的数据对于每个内部节点 V 所有 key 小于 V 的都被存储在 V 的左子树所有 key 大于 V 的都存储在 V 的右子树 注意这个限制条件可别和堆搞混了。说白了就是对于每个内部节点左子树的 key 都比它小右子树都比它大。 如果中序遍历(二叉树遍历讲过了)这颗二叉树你会发现输出的顺序正好是有序的。 我们先来定义一下 BST 的节点结构 class BSTNode(object):def __init__(self, key, value, leftNone, rightNone):self.key, self.value, self.left, self.right key, value, left, right构造一个 BST 我们还像之前构造二叉树一样按照上图构造一个 BST 用来演示 class BST(object):def __init__(self, rootNone):self.root rootclassmethoddef build_from(cls, node_list):cls.size 0key_to_node_dict {}for node_dict in node_list:key node_dict[key]key_to_node_dict[key] BSTNode(key, valuekey) # 这里值暂时用 和 key一样的for node_dict in node_list:key node_dict[key]node key_to_node_dict[key]if node_dict[is_root]:root nodenode.left key_to_node_dict.get(node_dict[left])node.right key_to_node_dict.get(node_dict[right])cls.size 1return cls(root)NODE_LIST [{key: 60, left: 12, right: 90, is_root: True},{key: 12, left: 4, right: 41, is_root: False},{key: 4, left: 1, right: None, is_root: False},{key: 1, left: None, right: None, is_root: False},{key: 41, left: 29, right: None, is_root: False},{key: 29, left: 23, right: 37, is_root: False},{key: 23, left: None, right: None, is_root: False},{key: 37, left: None, right: None, is_root: False},{key: 90, left: 71, right: 100, is_root: False},{key: 71, left: None, right: 84, is_root: False},{key: 100, left: None, right: None, is_root: False},{key: 84, left: None, right: None, is_root: False}, ] bst BST.build_from(NODE_LIST)BST 操作 查找 如何查找一个指定的节点呢根据定义我们知道每个内部节点左子树的 key 都比它小右子树的 key 都比它大所以 对于带查找的节点 search_key从根节点开始如果 search_key 大于当前 key就去右子树查找否则去左子树查找。 一直到当前节点是 None 了说明没找到对应 key。 好撸代码 def _bst_search(self, subtree, key):if subtree is None: # 没找到return Noneelif key subtree.key:return self._bst_search(subtree.left, key)elif key subtree.key:return self._bst_search(subtree.right, key)else:return subtreedef get(self, key, defaultNone):node self._bst_search(self.root, key)if node is None:return defaultelse:return node.value获取最大和最小 key 的节点 其实还按照其定义最小值就一直向着左子树找最大值一直向右子树找递归查找就行。 def _bst_min_node(self, subtree):if subtree is None:return Noneelif subtree.left is None: # 找到左子树的头return subtreeelse:return self._bst_min_node(subtree.left)def bst_min(self):node self._bst_min_node(self.root)return node.value if node else None插入 插入节点的时候我们需要一直保持 BST 的性质每次插入一个节点我们都通过递归比较把它放到正确的位置。 你会发现新节点总是被作为叶子结点插入。请你思考这是为什么 def _bst_insert(self, subtree, key, value): 插入并且返回根节点:param subtree::param key::param value:if subtree is None: # 插入的节点一定是根节点包括 root 为空的情况subtree BSTNode(key, value)elif key subtree.key:subtree.left self._bst_insert(subtree.left, key, value)elif key subtree.key:subtree.right self._bst_insert(subtree.right, key, value)return subtreedef add(self, key, value):node self._bst_search(self.root, key)if node is not None: # 更新已经存在的 keynode.value valuereturn Falseelse:self.root self._bst_insert(self.root, key, value)self.size 1return True删除节点 删除操作相比上边的操作要麻烦很多首先需要定位一个节点删除节点后我们需要始终保持 BST 的性质。 删除一个节点涉及到三种情况 节点是叶节点节点有一个孩子节点有两个孩子 我们分别来看看三种情况下如何删除一个节点 删除叶节点 这是最简单的一种情况只需要把它的父亲指向它的指针设置为 None 就好。 删除只有一个孩子的节点 删除有一个孩子的节点时我们拿掉需要删除的节点之后把它的父亲指向它的孩子就行因为根据 BST 左子树都小于节点右子树都大于节点的特性删除它之后这个条件依旧满足。 删除有两个孩子的内部节点 假如我们想删除 12 这个节点改怎么做呢你的第一反应可能是按照下图的方式 但是这种方式可能会影响树的高度降低查找的效率。这里我们用另一种非常巧妙的方式。 还记得上边提到的吗如果你中序遍历 BST 并且输出每个节点的 key你会发现就是一个有序的数组。 [1 4 12 23 29 37 41 60 71 84 90 100]。这里我们定义两个概念逻辑前任(predecessor)和后继(successor)请看下图: 12 在中序遍历中的逻辑前任和后继分别是 4 和 23 节点。于是我们还有一种方法来删除 12 这个节点 找到待删除节点 N(12) 的后继节点 S(23)复制节点 S 到节点 N从 N 的右子树中删除节点 S并更新其删除后继节点后的右子树 说白了就是找到后继并且替换这里之所以能保证这种方法是正确的你会发现替换后依旧是保持了 BST 的性质。 有个问题是如何找到后继节点呢待删除节点的右子树的最小的节点不就是后继嘛上边我们已经实现了找到最小 key 的方法了。 我们开始编写代码实现和之前的操作类似我们还是通过辅助函数的形式来实现这个递归函数会比较复杂请你仔细理解: def _bst_remove(self, subtree, key):删除节点并返回根节点if subtree is None:return Noneelif key subtree.key:subtree.left self._bst_remove(subtree.left, key)return subtreeelif key subtree.key:subtree.right self._bst_remove(subtree.right, key)return subtreeelse: # 找到了需要删除的节点if subtree.left is None and subtree.right is None: # 叶节点返回 None 把其父亲指向它的指针置为 Nonereturn Noneelif subtree.left is None or subtree.right is None: # 只有一个孩子if subtree.left is not None:return subtree.left # 返回它的孩子并让它的父亲指过去else:return subtree.rightelse: # 俩孩子寻找后继节点替换并从待删节点的右子树中删除后继节点successor_node self._bst_min_node(subtree.right)subtree.key, subtree.value successor_node.key, successor_node.valuesubtree.right self._bst_remove(subtree.right, successor_node.key)return subtreedef remove(self, key):assert key in selfself.size - 1return self._bst_remove(self.root, key)完整代码你可以在本章的 bst.py 找到。 另外推荐一个可以在线演示过程的网址大家可以手动执行下看看效果 https://www.cs.usfca.edu/~galles/visualization/BST.html 时间复杂度分析 上边介绍的操作时间复杂度和二叉树的形状有关。平均来说时间复杂度是和树的高度成正比的树的高度 h 是 log(n) 但是最坏情况下以上操作的时间复杂度都是 O(n)。为了改善 BST 有很多变种感兴趣请参考延伸阅读中的内容。 源码 # -*- coding: utf-8 -*-class BSTNode(object):def __init__(self, key, value, leftNone, rightNone):self.key, self.value, self.left, self.right key, value, left, rightclass BST(object):def __init__(self, rootNone):self.root rootclassmethoddef build_from(cls, node_list):cls.size 0key_to_node_dict {}for node_dict in node_list:key node_dict[key]key_to_node_dict[key] BSTNode(key, valuekey) # 这里值暂时用 和 key一样的for node_dict in node_list:key node_dict[key]node key_to_node_dict[key]if node_dict[is_root]:root nodenode.left key_to_node_dict.get(node_dict[left])node.right key_to_node_dict.get(node_dict[right])cls.size 1return cls(root)def _bst_search(self, subtree, key):if subtree is None: # 没找到return Noneelif key subtree.key:return self._bst_search(subtree.left, key)elif key subtree.key:return self._bst_search(subtree.right, key)else:return subtreedef __contains__(self, key):实现 in 操作符return self._bst_search(self.root, key) is not Nonedef get(self, key, defaultNone):node self._bst_search(self.root, key)if node is None:return defaultelse:return node.valuedef _bst_min_node(self, subtree):if subtree is None:return Noneelif subtree.left is None: # 找到左子树的头return subtreeelse:return self._bst_min_node(subtree.left)def bst_min(self):node self._bst_min_node(self.root)return node.value if node else Nonedef _bst_insert(self, subtree, key, value): 插入并且返回根节点:param subtree::param key::param value:if subtree is None: # 插入的节点一定是根节点包括 root 为空的情况subtree BSTNode(key, value)elif key subtree.key:subtree.left self._bst_insert(subtree.left, key, value)elif key subtree.key:subtree.right self._bst_insert(subtree.right, key, value)return subtreedef add(self, key, value):node self._bst_search(self.root, key)if node is not None: # 更新已经存在的 keynode.value valuereturn Falseelse:self.root self._bst_insert(self.root, key, value)self.size 1return Truedef _bst_remove(self, subtree, key):删除节点并返回根节点if subtree is None:return Noneelif key subtree.key:subtree.left self._bst_remove(subtree.left, key)return subtreeelif key subtree.key:subtree.right self._bst_remove(subtree.right, key)return subtreeelse: # 找到了需要删除的节点if subtree.left is None and subtree.right is None: # 叶节点返回 None 把其父亲指向它的指针置为 Nonereturn Noneelif subtree.left is None or subtree.right is None: # 只有一个孩子if subtree.left is not None:return subtree.left # 返回它的孩子并让它的父亲指过去else:return subtree.rightelse: # 俩孩子寻找后继节点替换并删除其右子树的后继节点同时更新其右子树successor_node self._bst_min_node(subtree.right)subtree.key, subtree.value successor_node.key, successor_node.valuesubtree.right self._bst_remove(subtree.right, successor_node.key)return subtreedef remove(self, key):assert key in selfself.size - 1return self._bst_remove(self.root, key)NODE_LIST [{key: 60, left: 12, right: 90, is_root: True},{key: 12, left: 4, right: 41, is_root: False},{key: 4, left: 1, right: None, is_root: False},{key: 1, left: None, right: None, is_root: False},{key: 41, left: 29, right: None, is_root: False},{key: 29, left: 23, right: 37, is_root: False},{key: 23, left: None, right: None, is_root: False},{key: 37, left: None, right: None, is_root: False},{key: 90, left: 71, right: 100, is_root: False},{key: 71, left: None, right: 84, is_root: False},{key: 100, left: None, right: None, is_root: False},{key: 84, left: None, right: None, is_root: False}, ]def test_bst_tree():bst BST.build_from(NODE_LIST)for node_dict in NODE_LIST:key node_dict[key]assert bst.get(key) keyassert bst.size len(NODE_LIST)assert bst.get(-1) is None # 单例的 None 我们用 is 来比较assert bst.bst_min() 1bst.add(0, 0)assert bst.bst_min() 0bst.remove(12)assert bst.get(12) is Nonebst.remove(1)assert bst.get(1) is Nonebst.remove(29)assert bst.get(29) is None练习题 请你实现查找 BST 最大值的函数 延伸阅读 《Data Structures and Algorithms in Python》14 章树的概念和算法还有很多我们这里介绍最基本的帮你打个基础了解红黑树。普通二叉查找树有个很大的问题就是难以保证树的平衡极端情况下某些节点可能会非常深导致查找复杂度大幅退化。而平衡二叉树就是为了解决这个问题。请搜索对应资料了解下。了解 mysql 索引使用的 B-Tree 结构(多路平衡查找树)这个是后端面试数据库的常考点。想想为什么当元素非常多的时候二叉树的深度会很深导致多次磁盘查找。从B树、B树、B*树谈到R 树 Leetcode 验证是否是合法二叉搜索树 [validate-binary-search-tree](https://leetcode.com/problems/validate-binary-search-tree/

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

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

相关文章

电商平台排名南通做网站优化的公司

文章目录 一、项目整体框架一、传感器配置与驱动二、IMX222 1080P 模式图像解析(bayer 2 rgb 模块)2.1 解析有效像素(gen_sync)2.1.1同步字详细介绍: 2.2 bayer 2 rgb 一、项目整体框架 一、传感器配置与驱动 camera信息:索尼IMX222摄像头 SPI&#xf…

商城微网站建设多少钱wordpress 淘宝分享插件下载

昨日晚间,学校值班,在楼道里面巡查几遍之后发现无异常情况,接着就去值班室中打开电脑忙自己的事。过了没一会儿,3班三学生去找我了,对我说,最近班里的学习情况不是太好,部分学生上课容易打盹&am…

湖南至诚建设机械有限公司网站百度网站首页入口

写在前: 这一篇博客主要来初步的记录以下泛型的相关内容,内容比较琐碎,就不进行目录的整合,后续可能会对泛型这里进行系统性的梳理,此篇博客主要是对泛型有一个简单的认识与理解,需要知晓的内容。 当我调用…

泰州网站设计咨询wordpress数据库更改密码

PHP中,报错函数error_reporting()用于规定应该报告何种PHP错误,语法“error_reporting(level)”;使用该函数可以设置在脚本运行时的错误级别,如果没有设置可选参数level,则仅返回当前的错误报告级别。推荐:…

品牌形象网站源码北京网站优化企业

建议11: 区别对待和Equals在开始本建议之前,首先要明确概念“相等性”。CLR中将“相等性”分为两类:“值相等性”和“引用相等性”。如果用来比较的两个变量所包含的数值相等,那么将其定义为“值相等性”;如果比较的两…

哪些网站论坛做推广好莱芜网络小说作家

Squid 是一个代理和缓存服务器,它将请求转发到所需的目的地,同时保存请求的内容,当你再次请求相同内容时,他可以向你提供缓冲内容,从而提高访问速度。Squid代理服务器目前支持的协议有:http、SSL、DNS、FTP…

海南网站推广建设做网站的北京

目录 【设计模式专题之建造者模式】4. 自行车加工【设计模式专题之原型模式】5. 矩形原型 【设计模式专题之建造者模式】4. 自行车加工 文章链接&#xff1a;卡码网设计模式 题目链接&#xff1a;4. 自行车加工 注意重载<<函数的写法和使用方式&#xff0c;使用时与其它重…

网站建设常用的英文电商首页模板网站

介绍&#xff1a; Keras Tuner是一种用于优化Keras模型超参数的开源Python库。它允许您通过自动化搜索算法来寻找最佳的超参数组合&#xff0c;以提高模型的性能。Keras Tuner提供了一系列内置的超参数搜索算法&#xff0c;如随机搜索、网格搜索、贝叶斯优化等。它还支持自定义…

东莞网站建设实例推荐手机网站模板安装方法

背景 警告: BASE64Decoder是内部专用 API, 可能会在未来发行版中删除”或“警告: BASE64Encoder是内部专用 API, 可能会在未来发行版中删除 BASE64Encoder是在sun.misc包下&#xff0c;即&#xff1a;sun.misc.BASE64Encoder。这是sun公司的内部方法&#xff0c;不在jdk标准库…

网站注册表单怎么做wordpress会员查看

在公布两年之后&#xff0c;华为的鸿蒙系统历尽千难万险&#xff0c;蓄势待发&#xff0c;即将在6月2日的线上发布会上正式发布。对于鸿蒙的前景&#xff0c;通信行业的 5G 专家项立刚在接受采访中&#xff0c;在谈到对鸿蒙的看法时&#xff0c;他表示他相信 7 年后鸿蒙会成为全…

网站搭建制作公司wordpress落叶插件

这篇文章主要介绍了Ajax 设置Access-Control-Allow-Origin实现跨域访问,非常不错&#xff0c;具有参考借鉴价值&#xff0c;需要的朋友可以参考下ajax跨域访问是一个老问题了&#xff0c;解决方法很多&#xff0c;比较常用的是JSONP方法&#xff0c;JSONP方法是一种非官方方法&…

优质的seo网站排名优化软件wordpress批注功能

深入探索Logback日志框架的原理分析和开发实战指南系列 Logback日志框架Logback基本模块logback-corelogback-classiclogback-accessLogback的核心类LoggerAppenderLayoutLayout和Appender filterlogback模块和核心所属关系 Logbackj日志级别日志输出级别日志级别介绍 Logback的…

吉林省长春网站建设鄱阳网站建设多少钱

什么是神经网络&#xff1f; 神经网络是一个具有相连节点层的计算模型&#xff0c;其分层结构与大脑中的神经元网络结构相似。神经网络可通过数据进行学习&#xff0c;因此&#xff0c;可训练其识别模式、对数据分类和预测未来事件。 神经网络将您的输入细分为多个抽象层。比…

中国网站建设公司图片荆州市城市建设档案馆网站

1、环境搭建测试 虚拟机网络环境配置&#xff0c;模拟外网和内网 主机操作系统网络内网ip外网ip物理主机window10vmnet8192.168.70.1攻击机kali Linuxvmnet8192.168.70.134域控主机win server 2008 r2vmnet0192.168.52.138域成员主机win server 2k3vmnet0192.168.52.141服务器…

微网站设计与开发竞赛网站开发开源代码

文章目录 一、条件渲染1、v-if2、v-else3、v-else-if4、\<template> 上的 v-if5、v-show 二、区别&#xff1a;1、渲染区别2、性能区别&#xff1a; 三、v-if和v-for的优先级四、注意事项 一、条件渲染 1、v-if v-if 指令用于条件性地渲染一块内容。这块内容只会在指令…

电商网站建设服务wordpress临时关站

MySQL数据库的备份与恢复是数据库管理中至关重要的一环&#xff0c;它确保了数据的安全性和可恢复性。在本文中&#xff0c;我们将深入讨论如何进行MySQL数据库的备份和恢复&#xff0c;并详解物理备份和逻辑备份的概念及区别。 1. 如何备份和恢复MySQL数据库&#xff1f; 1.…

政务类网站苏州吴江建设局招投标网站

网络大厂 AI研究团队近日在最新的Pixel相机中&#xff0c;于无快门模式Photobooth新增亲吻侦测功能&#xff0c;当用户亲吻自己的爱人时&#xff0c;相机会自动捕捉这一瞬间。网络大厂过去是藉由Photobooth模式&#xff0c;让用户更简单地成功自拍&#xff0c;不管是一个人、情…

自己做网站好还是购买网站好上海公共招聘网官网下载

2023年山东省职业院校技能大赛高职组信息安全管理与评估 理论题 理论技能与职业素养&#xff08;100分&#xff09; 2023年山东省职业院校技能大赛高职组信息安全管理与评估 理论题 【注意事项】 Geek极安云科专注技能竞赛技术提升&#xff0c;基于各大赛项提供全面的系统性…

网页游戏网站火网站备案取消 后果

我国网络购物用户规模8.12亿占网民整体80.3%&#xff08;来源&#xff1a;中商产业研究院&#xff09;。由此可见&#xff0c;网络购物逐渐成为人们普遍选择的一种消费方式。作为连接买卖双方的服务方&#xff0c;电商平台掌握了海量的用户数据&#xff0c;用户数据作为一种宝贵…

广州万户网站公司wordpress 去购买按钮

用户功能&#xff1a; 登录后要有一个首页 比如:可以看见目前的耗材消耗记录&#xff0c;可做成图表菜单栏在左侧显示 1.个人信息管理 可以对基本信息进行修改&#xff0c;(修改密码时需要验证) 2.耗材管理&#xff08;耗材信息&#xff09; 普通用户可以查询当前相关耗材信息[…