我有以下二进制搜索树,有根节点20.我试图回答的问题是,如果我们应用函数t = deleteRoot(t)
,那么新根节点的值也是如此作为其直接的左右儿童(例如,当前的根节点是20,左边的孩子11和右边的孩子32)。在过去的两个小时里,我试图解决这个问题,至少写了10页,但这次递归正在扼杀我。有人可以帮助我想象这一点 - 即一些思考方式,让我可以处理递归。我不太擅长可视化递归如何工作,但我可以在某种程度上实现它。非常感谢。顺便说一句,答案是根节点:21,左子11和右子32。
我的尝试:
问题告诉我们从t=deleteRoot(t)
开始。
parent = node containing 25
succ = node containing 21
succval = 21
然后我们到达
t = TreeDelete(t, succval)
然后我对TreeDelete函数如何工作有点迷失
t->left = TreeDelete(t->left, key) ...etc
deleteRoot(树t)功能
// delete root of tree
Tree deleteRoot(Tree t)
{
Link newRoot;
// if no subtrees, tree empty after delete
if (t->left == NULL && t->right == NULL) {
free(t);
return NULL;
}
// if only right subtree, make it the new root
else if (t->left == NULL && t->right != NULL) {
newRoot = t->right;
free(t);
return newRoot;
}
// if only left subtree, make it the new root
else if (t->left != NULL && t->right == NULL) {
newRoot = t->left;
free(t);
return newRoot;
}
// else (t->left != NULL && t->right != NULL)
// so has two subtrees
// - find inorder successor (grab value)
// - delete inorder successor node
// - move its value to root
Link parent = t;
Link succ = t->right; // not null!
while (succ->left != NULL) {
parent = succ;
succ = succ->left;
}
int succVal = succ->value;
t = TreeDelete(t,succVal);
t->value = succVal;
return t;
}
树TreeDelete(树t,密钥k)功能:
Tree TreeDelete(Tree t, Key k)
{
Tree deleteRoot(Tree);
if (t == NULL)
return NULL;
int diff = cmp(k,key(t->value));
if (diff == 0)
t = deleteRoot(t);
else if (diff < 0)
t->left = TreeDelete(t->left, k);
else if (diff > 0)
t->right = TreeDelete(t->right, k);
return t;
}
答案 0 :(得分:1)
顺便说一下,答案是根节点:21,左子11和右子32。
嗯,它是一个解决方案,但不是唯一的解决方案。
左边的孩子11和右边的孩子32也是一个解决方案。删除根时,可以选择新根
或
因此,将所选节点的值复制到当前根目录。然后删除所选节点。如果所选节点有子节点,则可以递归重复该过程。
答案 1 :(得分:1)
在删除的情况下,如果要删除的节点有两个子节点:
后继是右子树中的最高元素,而前一个是左子树中的最低元素。在你的情况下,继任者将是21,而前任将是18。