Realloc causing program to crash

杀马特。学长 韩版系。学妹 提交于 2019-12-13 04:55:24

问题


Currently trying to write menu based program that asks user for student records, after initial records are entered I want user to have option to add more record slots but when I try to realloc my 2d pointer array my program crashes, specifically after the 2nd function is called.

#include <stdio.h> 
#include <string.h>
#include <stdlib.h>
#define LENGTH 21
void printRecords(int* size, char **fistName, char **lastName, float *grade);
void addRecord(int* size, char** firstName, char** lastName, float *grade);

int  main(void) { /* Minimum measure check */
    int size = 0, *check = (int*)malloc(sizeof(int));
    *check = 1;
    while (check) {
        printf("Please indicate number of records you want to enter (min 5): ");
        scanf("%d", &size);
        if (size < 5)
            printf("Size entered was below the minimum.\n");
        else
            check = 0; }
    free(check);

                                        /* Dynamic Memory Allocation */
    char **firstName = (char**)malloc(size * sizeof(char*)), **lastName = (char**)malloc(size * sizeof(char*)); 
    float *grade = (float*)malloc(size * sizeof(float));

    int i;
    for (i = 0; i < size; i++) {
        firstName[i] = (char*)malloc(LENGTH *  sizeof(char));
        lastName[i] = (char*)malloc(LENGTH * sizeof(char)); }

    printf("Please input records of students (enter a new line after each record),\nwith following format first name last name score:\n");
    for (i = 0; i < size; (i)++)
        scanf("%s %s %f", &firstName[i][0], &lastName[i][0], &grade[i]);

    int option = 1;
    while (option != 0) { /* Option Menu */
        printf("Print records (press 1)\nAdd new record(press 2)\nDelete record(s)(press 3)\nSeach by last name(press 4)\nSort by score(press 5)\nSort by last name(press 6)\nFind the median score(press 7)\nExit the program(press 0)\n");
        scanf("%d", &option);

        switch (option) {
        case 1:
            printRecords(&size, firstName, lastName, grade);
            break;
        case 2:
            addRecord(&size, firstName, lastName, grade);
            break;
        case 3:
            break;
        case 4:
            break;
        case 5:
            break;
        case 6:
            break;
        case 7:
            break;
        }
    }
    return 0;
}

void printRecords(int* size, char **firstName, char **lastName, float grade[]) { /* Option 1 */
            int i;
            for (i = 0; i < *size; i++)
                printf("First Name : %s, Last Name : %s, Score : %.2f\n", firstName[i], lastName[i], grade[i]); 
    }

void addRecord(int* size, char** firstName, char** lastName, float* grade) { /* Option 2 */
    char **a;
    float *c;
    (*size) += 1;

    a = (char **)realloc(firstName, *size * sizeof(char*)); /* Error */
    if (a != NULL) //realloc was successful
        firstName = a;
    else //there was an error

    a = (char **)realloc(lastName, *size * sizeof(char*));
    if (a != NULL) //realloc was successful
        lastName = a;
    else; //there was an error 

    c = (float *)realloc(grade, *size * sizeof(float*));
    grade = c;
    firstName[*size - 1] = (char*)malloc(LENGTH * sizeof(char));
    lastName[*size - 1] = (char*)malloc(LENGTH * sizeof(char));
    scanf("%s %s %f", &firstName[*size][0], &lastName[*size][0], &grade[*size]);
    }

回答1:


EDIT there is an error in a missing ; resulting in lastName not being reallocated

if (a != NULL) //realloc was successful
    firstName = a;
else //there was an error                                  <<-- missing ;

a = (char **)realloc(lastName, *size * sizeof(char*));  // <<-- executed under "else"

In fact, lastName is assigned the same value as firstName with the following

if (a != NULL) //realloc was successful
    lastName = a;

Also, a comment about about your use of check. There are some things wrong with your input loop. It's quite unnecessary to allocate memory for a simple int. You aren't even using check as a pointer (check = 0; will cause free() to fail, and a memory leak).

int size = 0, *check = (int*)malloc(sizeof(int));
*check = 1;
while (check) {         // <==== error should be *check
    printf("Please indicate number of records you want to enter (min 5): ");
    scanf("%d", &size);
    if (size < 5)
        printf("Size entered was below the minimum.\n");
    else
        check = 0;      // <==== error should be *check
    }
free(check);

This would be much easier, and you don't even need check.

int size;
do {
    printf("Please indicate number of records you want to enter (min 5): ");
    scanf("%d", &size);
    if (size < 5)
        printf("Size entered was below the minimum.\n");
    }
while (size < 5);



回答2:


C is pass by value.

The changes applied to firstName and lastName in addREcord() are lost after the function returned, as those two vairbales carry copeis of the variables passed as argument to the call of addRecord().

Change the definition of addRecord() from

void addRecord(int* size, char** firstName, char** lastName, float* grade);

to be

void addRecord(int* size, char*** pfirstName, char*** plastName, float* grade);

and inside addRecord() replace all firstName with (*pfirstName) and all lastName with (*plastName)

(Interessting enough you did the correctly for size.)

Call addRecord() like this:

addRecord(&size, &firstName, &lastName, grade);


来源:https://stackoverflow.com/questions/29776167/realloc-causing-program-to-crash

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!