我知道使用旋转保持二叉搜索树平衡/自平衡的方法。
我不确定我的情况是否需要那么复杂。我不需要像自平衡BST那样维护任何排序顺序属性。我只是有一个普通的二叉树,我可能需要删除节点或插入节点。我需要尝试在树中保持平衡。为简单起见,我的二叉树类似于段树,每次删除一个节点时,从根到这个节点的路径上的所有节点都会受到影响(在我的情况下,这只是节点值的一些减法)。类似地,每次插入一个节点时,从根到插入节点的最终位置的所有节点都将受到影响(这次添加了节点值)。
要保持这样一棵树的平衡,最简单的方法是什么?它不需要像AVL树那样严格地保持高度平衡,但像RB树或稍微不平衡的树这样的东西也是可以接受的。
在平衡非BST时,要问的一个大问题是
你的树能有效地支持旋转吗?
某些类型的二叉树,比如k-d树,具有特定的逐层结构,使得旋转不可行。其他的,比如范围树,在每个节点中都有辅助元数据,在旋转后更新成本很高。但是如果你能处理旋转,那么你可以使用几乎任何一种平衡策略。最简单的选择可能是在踏板上为你的树建模:在每个节点中放入一个随机选择的权重字段,然后在插入过程中,向上旋转你新添加的叶子,直到它的权重小于它的父节点。要删除,用它较轻的子节点重复旋转节点,直到它是一个叶子,然后删除它。
如果你不能支持轮换,你需要一个不需要轮换的再平衡策略。也许最简单的选择是以替罪羊树为基础对你的树进行建模。替罪羊树的工作原理是,懒洋洋地检测一个太深的节点,使树无法平衡,然后将最小的不平衡子树重建成一棵完全平衡的树,使一切恢复正常。一旦节点数量下降了某个常数因子,就可以通过重建整个树来处理删除。
如果一个新节点不必插入到特定的位置——可能由它自己的值和树中的值决定——但您完全可以自由选择它的位置,那么您可以将树的形状保持为完整的树:
在一个完整的二叉树中,除了最后一层之外,每一层都是完全填充的,最后一层中的所有节点都尽可能地左移。
对于一棵完整的树来说,数组是一种非常有效的数据结构,因为您可以按广度优先遍历的顺序存储节点。因为树是完整的,所以数组没有间隙。此结构通常用于堆:
堆通常使用数组实现,如下所示:
一个完整的二进制最大堆的示例,其中节点密钥是1到100之间的整数,以及如何将其存储在数组中。
在数组中,第一个索引包含根元素。数组的下两个索引包含根的子级。接下来的四个索引包含根的两个子节点的四个子节点,以此类推。因此,给定索引i处的节点,其子节点位于索引2i 1和2i 2处,其父节点位于索引层((i-1)/2)。这种简单的索引方案可以有效地“向上”或“向下”移动树。
在您的情况下,您将定义插入/删除操作如下:
主要内容:二叉排序树转化为平衡二叉树,构建平衡二叉树的代码实现,总结上一节介绍如何使用二叉排序树实现动态 查找表,本节介绍另外一种实现方式—— 平衡二叉树。 平衡二叉树,又称为 AVL 树。实际上就是遵循以下两个特点的二叉树: 每棵子树中的左子树和右子树的深度差不能超过 1; 二叉树中每棵子树都要求是平衡二叉树; 其实就是在二叉树的基础上,若树中每棵子树都满足其左子树和右子树的深度差都不超过 1,则这棵二叉树就是平衡二叉树。 图 1 平衡与不平衡的二叉树及结点的
NowCoder 题目描述 平衡二叉树左右子树高度差不超过 1。 解题思路 // java private boolean isBalanced = true; public boolean IsBalanced_Solution(TreeNode root) { height(root); return isBalanced; } private int height(Tre
排序二叉树中存在一个问题就是可能会退化成一个链表,当只有左子树或者右子树有节点的时候,此时排序二叉树就像链表一样,但因为排序二叉树在插入查询的时候还要判断左右子树的问题,这样查询的效率反而变低,从而引出了平衡二叉树 平衡二叉树又称平衡搜索树(Self-balance Binary Search Tree)又称AVL树,同时保证了查询和添加的效率。首先平衡二叉树是一颗排序二叉树,且它是空树或者他的每
这里有问题 二叉搜索树(BST)是一种二叉树,其中每个节点的值大于或等于该节点左子树中所有节点的值,而小于该节点右子树中所有节点的值。 编写一个函数,根据使用的时间有效地检查给定的二叉搜索树是否包含给定的值。
我试图理解二叉树的属性。但有一件事我不确定: 二叉树的dev.表示: > 如果任意两片树叶的深度差最大为1,则二叉树是平衡的。 我问我这两个定义是否相等,我的意思是定义。1统计Def。2和viceversa?...对我来说似乎是的...但是谁能用例子准确地解释我这个属性的(非)等价? 谢谢,帕特里克
如果二叉树是使用递归的bst,我正在尝试编写一个bool函数来返回true,我需要一些关于haskell语法的指导。 我知道要使二叉树成为 bst,左侧子树必须始终仅包含小于头部的节点。并且右侧子树必须始终仅包含大于头部的节点。我正在这样构建我的函数: 但是此代码会导致错误: 无法将预期类型“Bool”与实际类型“Int”匹配 参考