Я не понимаю, почему я получаю ошибку сегментации в таком простом и понятном коде, пожалуйста, помогите. Я проверял код снова и снова, но не мог понять. Весь смысл кода состоит в том, чтобы проверить, могу ли я написать метод Insert, не возвращая указатель на узел.

#include<stdio.h>
#include<stdlib.h>


struct BSTNode
{
        int data;
        struct BSTNode *left;
        struct BSTNode *right;
};

struct BST
{
        struct BSTNode *root;
};

struct BST *CreateBST(void);
void Insert(struct BSTNode *root,int data);

int main(void)
{
        struct BST *tree = CreateBST();
        int a[6]= {0,1,2,3,4,5};
        int i;
        for(i=0;i<6;i++)
        {
                Insert(tree->root,a[i]);
        }
        return 0;
}

struct BST *CreateBST(void)
{
        return NULL;
}

void Insert(struct BSTNode *root,int data)
{
        if(root == NULL)
        {
                struct BSTNode *new_node = (struct BSTNode *) malloc (sizeof(struct BSTNode));
                if(!new_node)
                {
                        printf("Memory Error");
                        return;
                }
                new_node->data = data;
                new_node->left = NULL;
                new_node->right= NULL;
                root = new_node;
        }
        else if(data<= root->data)
                Insert(root->left,data);
        else if(data>root->data)
            Insert(root->right,data);
    return;
}
-1
Rajesh 7 Авг 2014 в 14:51
1
Если root имеет значение null, например, потому что вы вызвали его через Insert(root->left,data); и выделили новый корень, будет ли он сохранен обратно в root->left в предыдущем вызове в стеке вызовов?
 – 
Lasse V. Karlsen
7 Авг 2014 в 14:52
Скомпилируйте со всеми предупреждениями и отладочной информацией (например, gcc -Wall -g при использовании GCC...). Затем узнайте, как использовать отладчик (например, gdb). В Linux также может помочь использование valgrind.
 – 
Basile Starynkevitch
7 Авг 2014 в 14:57

2 ответа

Лучший ответ

Вы вызываете функцию CreateBST, которая возвращает NULL. Затем вы пытаетесь разыменовать этот указатель NULL, выполнив tree->root. Это приведет к неопределенному поведению и вашему сбою.


Есть и другие проблемы с вашей программой, например (если вы решите вышеуказанную проблему) вы передаете tree->root по значению в Insert, что означает, что внутри {{X2 }} function root является копией, и изменение копии не изменит оригинал.

3
Some programmer dude 7 Авг 2014 в 14:56

Ошибка сегментации возникает, когда программа пытается получить доступ к зоне памяти, которая не находится в ее компетенции. Попробуйте перезагрузиться, возможно, это исправит ошибку.

-3
Azazel 7 Авг 2014 в 14:55
3
Перезагрузка почти никогда не исправляет segfault. OP разыменовывает указатель NULL, перезагрузка не может волшебным образом исправить плохой код
 – 
Elias Van Ootegem
7 Авг 2014 в 14:57