我在C中实现了BST。插入和查找工作正常。但删除根节点时删除存在问题。我无法释放指向根节点的指针。如果我将它作为双指针传递,我可以,但我想保持代码简单而不使用双指针。这里我没有指向根节点的头指针。我应该使用指向根节点的头指针吗?
#include<stdio.h>
#include<stdlib.h>
struct node
{
int data;
struct node* left;
struct node* right;
};
struct node* newNode(int data)
{
struct node* node = malloc(sizeof(struct node));
node->data=data;
node->left=NULL;
node->right=NULL;
return(node);
}
static int lookup(struct node* node,int target)
{
if(node==NULL)
{
return(0);
}
else
{
if(target == node->data)
{
return(1);
}
else
{
if(target < node->data)
{
return(lookup(node->left,target));
}
else
{
return(lookup(node->right,target));
}
}
}
}
struct node* insert(struct node* node, int data)
{
if(node==NULL)
{
return(newNode(data));
}
else
{
if(data < node->data)
{
node->left =insert(node->left,data);
}
else
{
node->right=insert(node->right,data);
}
return(node);
}
}
struct node* delete(struct node* node, struct node* pnode, int target)
{
struct node* rchild;
struct node* rchildparent;
if(node==NULL)
{
return(pnode);
}
else
{
if(target == node->data)
{
if(node->left == NULL && node->right == NULL) //leaf node
{
if(pnode == NULL) //special case deleting the root node
{
free(node);
return(NULL);
}
if(pnode->left == node)
{
pnode->left = NULL;
}
else
{
pnode->right = NULL;
}
free(node);
return(pnode);
}
if(node->left ==NULL ) //one child
{
if(pnode == NULL) //deleting root having no left child
{
struct node* temp = node;
node = node->right;
free(temp);
return(node);
}
if(pnode->left == node)
{
pnode->left = node->right;
}
else
{
pnode->right = node->right;
}
free(node);
return(pnode);
}
if(node->right ==NULL ) //one child
{
if(pnode == NULL) //deleting root having no right child
{
struct node* temp = node;
node = node->left;
free(temp);
return(node);
}
if(pnode->left == node)
{
pnode->left = node->left;
}
else
{
pnode->right = node->left;
}
free(node);
return(pnode);
}
//two children case
rchild = node->right;
rchildparent=node;
while(rchild->left != NULL)
{
rchildparent=rchild;
rchild = rchild->left;
}
node->data=rchild->data;
if(rchildparent == node)
{
//rchildparent->right=rchild->right;
node->right=rchild->right;
}
else
{
//rchildparent->left=NULL;
rchildparent->left=rchild->right;
}
free(rchild);
if(pnode ==NULL) //root node
{
return(node);
}
return(pnode);
}
else
{
if(target < node->data)
{
delete(node->left,node,target);
return(node);
}
else
{
delete(node->right,node,target);
return(node);
}
}
}
}
void printinorder(struct node* node)
{
if(node == NULL)
{
return;
}
printinorder(node->left);
printf("%d\t",node->data);
printinorder(node->right);
}
int main()
{
clock_t start,end;
struct node* root = newNode(3);
insert(root,7);
insert(root,7);
insert(root,7);
printinorder(root);
printf("\n");
root = delete(root,NULL,6);
printinorder(root);
printf("\n");
}
编辑:
根据@ modifiable lvalue
建议修复了代码。现在有一种方法可以改进删除逻辑吗?
答案 0 :(得分:1)
我会从delete中返回头节点,并在主函数中管理头部,如:root = delete(root, NULL, 10);
,我会对insert:root = insert(root,/*...*/);
执行相同操作,因为它有点像看起来你已经完成了......
答案 1 :(得分:0)
私有DataNode删除(DataNode root,int dValue){
RSolr::Error::Http (RSolr::Error::Http - 500 Internal Server Error
Error: {'error'=>{'msg'=>'java.lang.AbstractMethodError','trace'=>'java.lang.RuntimeException: java.lang.AbstractMethodError
}
私有DataNode MinBST(DataNode root){
DataNode temp=null;
if(root!=null){
if(dValue<root.value){
root.left=delete(root.left,dValue);
}
else if(dValue>root.value){
root.right=delete(root.right,dValue);
}
else{
if(root.left==null){
temp=root.right;
root.right=null;
return temp;
}
else if(root.right==null){
temp=root.left;
root.left=null;
return temp;
}
temp=MinBST(root.right);
root.value=temp.value;
//deleting inorder successor
root.right=null;
}
}
return root;
}
浏览链接以从二叉树中删除节点
答案 2 :(得分:0)
{
"Version": "2012-10-17",
"Statement": [
{
"Sid": "Stmt1477112217000",
"Effect": "Allow",
"Action": [
"sns:Publish"
],
"Resource": [
"arn:aws:sns:ap-southeast-2:012345678912:My-SNS-Topic"
]
}
]
}