0

我正在尝试使用以下结构创建学生的链接列表。

struct student 
{
    int student_ID;
    char *student_name;
    struct course *courses_enrolled;
    Student *child;
};

//Insert student to the list with a given student pointer and the starting point
Student *insert_student(Student *child, Student *root)
{
    Student *temp = (Student*)malloc(sizeof(Student));
    //if there isn't a starting point, declare this as the start point
    if( root->student_name == NULL )
    {
        root->student_ID = child->student_ID;
        root->student_name = strdup(child->student_name;);
        root->child = NULL;
    }
    //if this student's name is before current node, replace node.
    else if( strcmp( child->student_name, root->student_name ) < 0 )
    {
        temp = root;
        root = child;
        child->child = temp;
    }
    //if this student's name is after current node, keep doing insert recursion
    else if( strcmp( child->student_name, root->student_name ) > 0 )
    {
        insert_student( child, root->child );
    }

    return root;
}

第一个根插入总是可以正常工作,但是当我尝试添加第二个时,程序将在第二次调用 insert_student 后出现段错误。比较失败

if( root->student_name == NULL )

我怀疑这与我访问根的子节点(root->child)有关,但我不确定是什么。

p/s:我知道我没有取消分配,这只是暂时的事情,因为我需要使用不同的库。

更新:删除了多余的代码。

4

3 回答 3

1

找到确切的问题有点困难,因为我们没有给出这个函数是如何调用的。似乎有几件事要检查。

我假设您传递给函数的childandroot确实已分配,根中的所有字段都设置为NULL并且该学生的姓名是有序的,因此您的第二个分支永远不会发生。然后,第一次插入将起作用。

但是,当您进行第二次插入时。您正在传递root->childNULL在第一if个子句中设置的内容。这将导致随后strcmp失败,因为您无法取消引用NULL(例如NULL->student_name引发错误)。

于 2012-09-30T19:50:58.793 回答
0

当您递归调用 insert_student 时,您应该确保您传递的值root不为空。如果它为空,您可能需要另一种情况(例如在末尾插入)。

我注意到的一件事是您从不使用temp. 它在使用前总是未使用或丢弃temp。我假设这不是你想要的。

此外,通常nextchild在结构中使用该词而不是在参数中使用类似newStudent或仅student代替 child 的词。

于 2012-09-30T19:40:13.520 回答
0
if( root->student_name == NULL )
{
    printf("Always here?\n");
    root->student_ID = child->student_ID;
    root->student_name = strdup(child->student_name);
    temp->student_ID = 0;
    temp->student_name = NULL;
    root->child = temp;
}

我发现实际上我需要将子节点的变量声明为 NULL 才能访问它们。

于 2012-09-30T19:50:30.120 回答