结构的C快速排序会导致分段错误



程序逐行从文件中读取信息并将信息存储在结构中。除了对structs数组进行排序之外,其他一切都正常。例如,在最后打印结构(末尾包含的代码)时,它完全可以正常工作。

当我调用qsort时,会出现问题(分段错误)。

此外,打印students[0].lastName也可以,但打印students[1].lastName会返回一个(null),这也令人困惑。

我到处看了看,我的代码似乎与发布的排序结构的正确解决方案非常相似,所以我很困惑。

在main的头中定义结构:

// DEFINE STRUCT
typedef struct _StudentInformation  {
    int term;
    int studentId;
    char *lastName;
    char *firstName;
    char *subject;
    int catalogNumber;
    char *section;
} StudentInformation;

在主方法中分配结构(STUDENT_DATA=50):

// ALLOCATE AN ARRAY OF STUDENTS (STRUCT)
    StudentInformation *students;
    if ((students = malloc(STUDENT_DATA*sizeof(StudentInformation)))==NULL) {
        scanf("Error can't allocate enough students!n");
        exit(1);
}

问题:调用quicksort(8的原因是有8个条目有效且已加载,甚至少于8个条目无效):

qsort(students, 8, sizeof(StudentInformation), comparator);

快速排序比较器:

int comparator (const void * a, const void * b) {
    StudentInformation *s1 = (StudentInformation*)a;
    StudentInformation *s2 = (StudentInformation*)b;
    return strcmp(s1->lastName, s2->lastName);
}

我知道数据加载良好的原因是因为打印工作完全正常:

void printInformation (StudentInformation *students) {
    // PRINT EVERYTHING
        while(students->firstName!=NULL) {
            printf("%-s, %s %15d %4d %4s%d %7sn",
                    students->lastName,students->firstName,students->term,
                    students->studentId, students->subject,students->catalogNumber,
                    students->section);
            // Increment
            students=students+sizeof(StudentInformation);
        }
}

它打印的内容(我只包括打印的8个中的2个,没有打印NULLS):

Castille, Michael Jr            1201 103993269  CSE230     R03
Boatswain, Michael R.            1201 105515018  CSE230     R01

谢谢!

行:

if ((students = malloc(STUDENT_DATA*sizeof(StudentInformation)))==NULL)

为结构本身分配内存,但不为指针引用的字符串分配内存:

char *lastName;
char *firstName;
char *subject;
char *section;

每一个指针都占用了足够的内存。您需要为字符串单独分配内存:

if ((lastName = malloc((LAST_NAME_LEN + 1) * sizeof(char))) == NULL) {
  // Error
}
if ((firstName = ...

在调试跳弹错误时,向您不拥有的内存写入总是一个很好的方法,可以获得意想不到的教训:您最终可能会遇到segfault或内存损坏,但它可能位于与问题的实际来源完全无关的代码区域。

如果STUDENT_DATA>=8,只有一种可能的解释,那就是一个或多个lastName字段从未初始化,并且包含NULL或垃圾。如果初始化这些字段的循环与打印它的循环(使用students=students+sizeof(StudentInformation)而不是students++)包含相同的错误,这就是原因。

你说的是Calling quicksort (the reason for the 8 is because there are 8 entries

这是不正确的。您应该传递数组中元素的数量(在您的情况下为STUDENT_DATA)。

最新更新