首页 > 解决方案 > 分段错误错误 - C 中的二叉搜索树

问题描述

我正在尝试构建二叉搜索树。使用插入函数插入一个整数(仅使用 1 到 100 进行测试)并使用中序遍历将结果附加到文件中。但是,我遇到了分段错误错误。在 Macbook Pro 2020 上使用 Visual Studio 代码。还在 Windows 上的 Codeblocks 上进行了测试 - filename.exe 停止工作并崩溃。

#include <stdio.h>
#include <stdlib.h>
    
typedef struct node *BST;
    
struct node {
    int data;
    BST left;
    BST right;
};

BST insert(BST root, int number) {
    BST temp = NULL;
    if (root == NULL) {
        temp = *(BST *)malloc(sizeof(BST));
        temp->left = NULL;
        temp->right = NULL;
        temp->data = number;
        root = temp;
        }
    else if (root->data > number) {
        insert(root->left, number);
    }
    else {
        insert(root->right, number);
    }
    return root;
}

//returning null if number not found and pointer to root if found
BST find(BST root, int number) {
    if (root == NULL) {
        return NULL;
    }
    
    if (root->data > number) {
        find(root->left, number);
    }
    else if (root->data < number) {
        find(root->right, number);
    }
    else (root->data = number);
        return root;
}
    
//printing number to file
void inOrder (BST root, FILE *fp) {
    if (root == NULL) return;
    inOrder(root->left, fp);
    fprintf(fp, "%d", root->data);
    inOrder(root->right, fp);
}

int main() {
    BST root = NULL;
    int n = 100;
    int treeArray[n];
    for (int r = 0; r < n; r++) {
        treeArray[r] = r;
    }
    root = insert(root, treeArray[0]);
    for (int x = 1; x < n; x++) {
        insert(root, treeArray[x]);
    }
    
    FILE *treefile = fopen("print_tree.txt", "w");
    inOrder(root, treefile);
    fclose(treefile);
    return 0;
}
    
Error: /bin/sh: line 1: 44278 Segmentation fault: 11 *file path redacted*

我在这里做错了什么?:(

标签: cdata-structuresbinary-search-tree

解决方案


主要问题在于此声明:

temp = *(BST *)malloc(sizeof(BST));

正如其他答案中已经清楚解释的那样,我将跳过它。

所以你可以这样做:

temp = malloc(sizeof (struct node));

或者

// to add : this helps in case the type of temp ever changes,
temp = malloc(sizeof(*temp));

其他小的逻辑变化:

  • find函数中,不需要这个else if语句
    // = or == doesn't matter now
    else (root->data = number);
  • insert函数中,您忘记链接在根节点之后插入的节点。因此,每当您执行 时inorder traversal,您只会获得根节点,即0在您的情况下。

笔记:

typedef用于使代码更具可读性,但使用 typedef 隐藏指针会造成混乱。所以我建议不要 typedef 指针。


推荐阅读