请原谅我,如果有人问过,但我在搜索时无法找到它。所有搜索结果都是关于遍历二叉树,就好像正在搜索特定节点一样 - 因此它会结束向左或向右走,等等。
但是如何遍历更新树的大小呢?就像你在底部添加了一个新节点一样,你必须更新每个节点的大小以反映新的树大小。
假设这是原始树,你添加Z:
D D
/ \ / \
A S --> A S
/ / \
N N Z
(size = 4) (size = 5)
所以要更新大小,除非我想错了,你必须先更新下面的节点,然后才能更新它上面的节点。对? (要更新D,您必须先更新S和A)
那么,你将如何从根到底遍历,但从下往上更新?
答案 0 :(得分:0)
我仍然不确定您存储每个子树大小的用例是什么,但是在每次插入过程中很容易保持更新而不诉诸递归。为简单起见,我们假设您从以下定义开始:
public static class BSTNode
{
public BSTNode leftTree = null;
public BSTNode rightTree = null;
public int subtreeSize = 1;
public int value;
public BSTNode(int valToAdd){
value = valToAdd;
}
}
public static class BST
{
public BSTNode root;
//public void insert(int valToAdd)
}
在insert
的实现中,我们从根开始并遍历树以找到添加新值的适当位置。我们可以随时更新每个子树的大小。一个简单的实现可能如下所示:
public void insert(int valToAdd)
{
if(root == null){
root = new BSTNode(valToAdd);
return;
}
BSTNode parent = root;
BSTNode current = root;
while(current != null){
parent = current;
++current.subtreeSize;
if(valToAdd <= current.value){
current = current.leftTree;
}
else{
current = current.rightTree;
}
}
if(valToAdd <= parent.value){
parent.leftTree = new BSTNode(valToAdd);
}
else{
parent.rightTree = new BSTNode(valToAdd);
}
}
有些情况下,您希望从底部开始更新,例如跟踪子树高度(可能用于重新平衡)。假设BSTNode
定义现在是:
public static class BSTNode
{
public BSTNode leftTree = null;
public BSTNode rightTree = null;
public int height = 0;
public int value;
public BSTNode(int valToAdd){
value = valToAdd;
}
}
在insert
中,使用Stack
(或任何可提供LIFO语义的东西)来存储新插入节点的祖先。修改我们之前的简单示例:
public void insert(int valToAdd)
{
if(root == null){
root = new BSTNode(valToAdd);
return;
}
java.util.Stack<BSTNode> stack = new java.util.Stack<BSTNode>();
BSTNode parent = root;
BSTNode current = root;
while(current != null){
parent = current;
stack.push(current);
if(valToAdd <= current.value){
current = current.leftTree;
}
else{
current = current.rightTree;
}
}
if(valToAdd <= parent.value){
parent.leftTree = new BSTNode(valToAdd);
}
else{
parent.rightTree = new BSTNode(valToAdd);
}
int height = 1;
while(!stack.isEmpty()){
current = stack.pop();
current.height = Math.max(height, current.height);
++height;
}
}