C-删除整个BST时出错

C-删除整个BST时出错,c,binary-search-tree,C,Binary Search Tree,在删除整个BST的过程中,我似乎一辈子都不知道我的代码出了什么问题 我想既然这似乎没有问题: void emptyTree(BST **root){ if((*root)!=NULL){ emptyTree(&(*root)->left); emptyTree(&(*root)->right); free(*root); } } 那么整个问题就在于树中每个节点的初始条目。有人能指出这里出了什么问题吗

在删除整个BST的过程中,我似乎一辈子都不知道我的代码出了什么问题

我想既然这似乎没有问题:

void emptyTree(BST **root){ 
    if((*root)!=NULL){
        emptyTree(&(*root)->left);
        emptyTree(&(*root)->right);
        free(*root);
    }
}
那么整个问题就在于树中每个节点的初始条目。有人能指出这里出了什么问题吗

void insertNode(BST **root, BST *temp){
    if((*root)!=NULL){
        temp->parent = *root;   
        if(((*root)->value) < (temp->value))    
            insertNode(&(*root)->right,temp);
        else if(((*root)->value) > (temp->value)) 
            insertNode(&(*root)->left,temp);
        else if(((*root)->value) == (temp->value)){ 
            printf("The number %i is already in the tree.\n",temp->value);  
            return;
        }
    } else {
        *root = temp;
        printf("%i was added to the tree.\n",temp->value);
        return;
    }
}

void newNode(BST **root, int x){
    BST *newnode;

    newnode = (BST *)malloc(sizeof(BST));
    newnode->value = x;
    newnode->left = newnode->right = newnode->parent = NULL;

    insertNode(root,newnode);
} 
void insertNode(BST**root,BST*temp){
如果((*根)!=NULL){
temp->parent=*根目录;
如果(((*根)->值)<(温度->值))
插入节点(&(*根)->右侧,临时);
如果((*根)->值)>(温度->值))
插入节点(&(*根)->左,临时);
如果((*root)->value)=(temp->value)){
printf(“编号%i已在树中。\n”,temp->value);
返回;
}
}否则{
*根=温度;
printf(“%i已添加到树中。\n”,temp->value);
返回;
}
}
void newNode(BST**root,int x){
BST*新节点;
newnode=(BST*)malloc(sizeof(BST));
newnode->value=x;
newnode->left=newnode->right=newnode->parent=NULL;
insertNode(根,新节点);
} 

它编译、运行、完全正确地执行每个功能(包括一次删除一个节点的功能)。除了“全部删除”(空树)一个。它不会删除所有内容(?)。当我运行emptyTree函数时,它甚至没有显示错误。只有当我打印整棵树时才会出错

发生错误的原因是您释放了所有数据,但忘记指出元素不再包含有效数据。
也就是说,删除后,所有元素的
成员以及您自己的
本身仍然包含一个值;它们仍然包含原始值,但不再指向有效的、已分配的内存

该错误不会直接发生在
emptyTree
中,因为它从末端节点一直到顶部都起作用,并且没有理由检查“down”。但是,只要您尝试打印
根目录
(及其子目录),您就正在访问未分配的内存

插入

*root = NULL;
emptyTree
函数中

free(*root);
emptyTree
函数中修复它,或者在调用
emptyTree
后将
root
设置为NULL


就个人而言,我更喜欢前者,尽管这是一个小开销。这样,您只需要一个函数来删除一棵树,而不是递归函数加上一个也将根设置为NULL的包装器。

好吧,有一件事可能是这样的。您需要在调试器中逐步查看代码以了解发生了什么-这比通过查看代码来猜测错误要高效得多(或要求其他人也这样做)。你说有问题。你怎么知道?它会编译吗?运行?改为删除文件吗?你还可以添加一个
main
,其中显示,对于一些项目,你如何使用
newNode
insertNode
以及(1)编译和(2)的
emptyTree
显示了问题?请看。我在发布此问题几分钟后在那里写了*root=NULL,但我不确定它是否真的被解除分配,或者它是否只是链接到NULL,从而丢失了整个树。感谢您的澄清:)是的,您需要两者
free(x)
将指向的内存标记为free,但它对
x
没有任何作用<代码>x=NULLOpposite是否存在;你说你不再需要指针了,但是内存块保持分配状态,并且不能以任何方式释放。