尝试为二叉搜索树编写删除函数。我知道有三种可能的情况需要考虑,但我不确定从哪里开始。
我的麻烦主要源于这样一个事实,一旦我找到需要删除的节点,我需要在需要删除的节点之后将它的PARENT节点设置为节点。我应该使用游标来保留父节点吗?
我有节点的结构:
struct bt_node {
int data;
bt_node* left;
bt_node* right;
};
remove函数的定义如下:
void remove(bt_node** top_ref, int data);
感谢您的帮助!
答案 0 :(得分:0)
简单的方法是扩展搜索代码,以便在沿树向下移动时跟踪第二个引用中的“最后”父级。然后,这个“扩展”搜索返回节点和节点的父节点。
然后您通过删除功能使用该搜索功能,因此您不必在删除逻辑中执行任何花哨的操作。
答案 1 :(得分:0)
一种巧妙的方法是使用递归。您要求删除函数将对当前节点的引用返回给调用函数。这样您就可以轻松修改父节点。
以下是一些递归代码供您参考:
结构声明:
typedef struct node {
int info;
struct node* lchild;
struct node* rchild;
}NODE;
删除代码:
NODE* deleteElem(NODE* root, int elem) {
NODE* save;
if(root == NULL) {
printf("Element not in the tree !\n");
return;
}
if(root->info == elem) {
if(root->rchild == NULL && root->lchild == NULL) { // no child
free(root);
return NULL;
}
else if(root->rchild == NULL || root->lchild == NULL) { // one child
if(root->rchild == NULL) {
save = root->lchild;
free(root);
return save;
}
else {
save = root->rchild;
free(root);
return save;
}
}
else { // two children
save = findPred(root->lchild);
root->info = save->info;
root->lchild = deleteElem(root->lchild, root->info);
return root;
}
}
else if(root->info < elem) {
root->rchild = deleteElem(root->rchild, elem);
}
else if(root->info > elem) {
root->lchild = deleteElem(root->lchild, elem);
}
return root;
}
NODE* findPred(NODE* root) {
static NODE* pred;
if(root == NULL) {
return pred;
}
else {
pred = root;
return findPred(root->rchild);
}
}
P.S :对不起,我刚注意到你的功能的原型声明。我希望更改此代码以匹配您的原型声明应该不会太困难。
答案 2 :(得分:0)
你可以试试这个:
Private Sub Worksheet_SelectionChange(ByVal Target As Range)
If Target.Address = "$AB$12:$AD$13" Then
Range("B1").Copy
Range("E11").Copy
Sheets("Data").Range("B" & lastrow).PasteSpecial xlPasteValues
End If
End Sub