簡體   English   中英

如何使用 malloc 增加陣列大小?

[英]How can I increase the array size with malloc?

我試圖制作一個 function 在結構數組中添加一個成員,然后增加其維度。

void addMember(id **list, size_t *size)
{
    (*size)++;
    *list = *size == 1 ? malloc(sizeof(id)) : realloc(*list, *size * sizeof(id));

    if(!list) {
        printf("Dynamic allocation failed.\n");
        exit(1);
    }
    
    list[*size-1]->name = malloc (30 * sizeof(char));
    list[*size-1]->surname = malloc (30 * sizeof(char));
    list[*size-1]->number = malloc (15 * sizeof(char));

    if(!list[*size-1]->name || !list[*size-1]->surname || !list[*size-1]->number) {
        printf("Dynamic allocation failed.\n");
        exit(1);
    }

    printf("Name: ");
    fgets(list[*size-1]->name, 30, stdin);
    list[*size-1]->name[strcspn(list[*size-1]->name, "\n")] = 0;
    list[*size-1]->name = realloc (list[*size-1]->name, strlen(list[*size-1]->name) + 1 * sizeof(char));

    if(strcmp(list[*size-1]->name, "") == 0) {
        printf("You did not enter the name. Try again.\n");
        free(list[*size-1]->name);
        (*size)--;
        *list = realloc(*list, *size * sizeof(id));
        return;
    }

    printf("Surname: ");
    fgets(list[*size-1]->surname, 30, stdin);
    surname[*size-1]->surname[strcspn(list[*size-1]->surname, "\n")] = 0;
    surname[*size-1]->surname = realloc (list[*size-1]->surname, strlen(list[*size-1]->surname) + 1 * sizeof(char));

    if(strcmp(list[*size-1]->surname, "") == 0) {
        printf("You did not enter the surname. Try again.\n");
        free(list[*size-1]->surname);
        (*size)--;
        *list = realloc(*list, *size * sizeof(id));
        return;
    }

    printf("Number: ");
    fgets(list[*size-1]->number, 15, stdin);
    list[*size-1]->number[strcspn(list[*size-1]->number, "\n")] = 0;
    list[*size-1]->number = realloc (list[*size-1]->number, strlen(list[*size-1]->number) + 1 * sizeof(char));

    if(strcmp(list[*size-1]->number, "") == 0) {
        printf("You did not enter the number. Try again.\n");
        free(list[*size-1]->number);
        (*size)--;
        *list = realloc(*list, *size * sizeof(id));
        return;
    }
}

但是,當我嘗試將第二個成員添加到數組時遇到了問題。 事實上,在第二次調用期間,程序在這里返回了一個 EXC_BAD_ACCESS 錯誤: list[*size-1]->name = malloc (30 * sizeof(char)); . 相反,我可以毫無問題地輸入第一個數組成員。 我該如何解決? 結構是:

typedef struct {
    char *name;
    char *surname;
    char *number;
} id;

編輯:

這是主文件:
 #include <stdio.h> #include <stdlib.h> #include <time.h> #include "functions.h" int main() { id *list = NULL; size_t i, size = 0; int choice; srand((unsigned)time(NULL)); do { printf("Enter '1' to display all members, enter '2' to add a new member, enter '3' to exit: "); scanf("%d%*c", &choice); putchar('\n'); switch(choice) { case 1: if(size == 0) printf("There's no members.\n"); else for(i = 0; i < size; i++) printf("%s %s\n", list[i].name, list[i].surname); break; case 2: if(size < 30) addMember(&list, &size); break; } printf("Press start."); getchar(); putchar('\n'); } while(choice;= 3); free(list); return 0; }

list是指向id數組的指針,因此它應該是: (*list)[*size-1].name等。您可以節省一些麻煩並創建一些臨時變量以在 function 中使用。 在整個 function 中使用它們,然后將它們分配回 function 的末尾。

例子:

void addMember(id **list_original, size_t *size_original)
{
    id *list = *list_original;
    int size = *size_original;
 
    size++;
    list = size == 1 ? malloc(sizeof(id)) : realloc(list, size * sizeof(id));
    if (!list) return; // Nothing to do as original values are untouched
    list[size-1].name = malloc (30 * sizeof(char));
    // etc...

    *list_original = list;
    *size_original = size;
}

另一種選擇是將值包裝在結構中並將指向該結構的指針傳遞給 function:

typedef struct {
    id *list;
    size_t size;
} list_data;
void addMember(list_data *list)
{
   // If you pass NULL to realloc it acts like malloc
   id *tmp = realloc(list->list, (list->size + 1) * sizeof(id));
   if (!tmp) return;
   list->list = tmp;
   list->list[list->size].name = malloc(30);
   // etc...
   list->size += 1;
}
int main()
{
    list_data list = {NULL, 0};
    addMember(&list);
    // ....
}

旁注:在結果中使用傳遞給realloc的指針是不好的做法:

list = realloc(list, size * sizeof(id));

原因是如果realloc失敗了,原來的memory就丟失了。 使用臨時變量。

id *temp_list = realloc(list, size * sizeof(id));
if (temp_list) {
    list = temp_list;
    // Continue
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM