问题陈述:给定二进制搜索树(BST),将其转换为二叉树,使原始BST的每个密钥都更改为密钥加上BST中所有更大密钥的总和。
Input: BST
5
/ \
2 13
/ \
11 14
Output: The given BST is converted to following Binary Tree
43
/ \
45 27
/ \
38 14
我能够在网上挖出这段有用的代码,但我无法理解它。到目前为止,传递一个变量来维持前一个总和使我的理解变得更加复杂。
请注意用更好的代码解释解释。或者使下面的代码更直观。
public class BSTWithInts
{
private Node root;
private class Node
{
Node leftChild;
Integer item;
Node rightChild;
}
public void addsNodes()
{
addSumUtil(root, 0);
}
private int addSumUtil(Node node, int sum)
{
if(node == null)
return 0;
if ( node.rightChild != null )
{
sum = addSumUtil(node.rightChild, sum);
}
if ( node.leftChild != null )
{
sum = addSumUtil(node.leftChild, sum);
// why are we doing this here, shouldn't we just
// traverse right tree only first
}
node.item += sum;
sum = node.item;
return sum;
}
}
编辑:我刚刚意识到代码的运行方式不正常。
5
/ \
2 13
should give
18
/ \
20 13
and not
20
/ \
15 13
答案 0 :(得分:1)
要了解上述代码中的内容,您需要了解递归的工作原理。
开始理解这个问题的简单方法是在处理过程中使用System.out.println语句,让左右儿童更好地了解正在发生的事情:
if ( node.rightChild != null )
{
System.out.println("Accessing right child: "+node.rightChild.item);
sum = addSumUtil(node.rightChild, sum);
}
if ( node.leftChild != null )
{
System.out.println("Accessing left child: "+node.leftChild.item);
sum = addSumUtil(node.leftChild, sum);
// why are we doing this here, shouldn't we just
// traverse right tree only first
}
您将发现print语句的输出按以下顺序排列,从而确认每个节点的正确子节点在其左子节点之前被计算。
Accessing right child: 13
Accessing right child: 14
Accessing left child: 11
Accessing left child: 2
答案 1 :(得分:1)
想象一下你做这件事最简单的方法,记住它是一个搜索树,所以一切都井然有序。你想要从最高的数字开始。记录下来,不管它。然后是第二高的数字:为它添加最高数字,并保留一份副本,因为这也是"所有数字的总和高于第3个最高数字"。将其添加到第3个最高数字并保留总和,因为它将被添加到第4个最高数字。你拖动它的总和,每次增加当前数字(反之亦然)。当你得到最小的数字时,你已经得到了树的其余部分的总和,准备添加它。
另外,我认为您找到的代码是错误的,即使它在示例树上有效。它看起来应该更像:
private int addSumUtil(Node node, int sum)
{
if (node == null) {
return sum;
}
sum = addSumUtil(node.rightChild, sum);
sum = node.item += sum;
sum = addSumUtil(node.leftChild, sum);
return sum;
}
请注意,sum = addSumUtil(null, sum);
是noop。