2017-04-20 49 views
-3

我正在編寫一個程序來創建一個用於創建列表的結構,但我得到一個雙重空閒或損壞錯誤。我知道鏈表會更好的實現,但我想知道我在這裏做錯了什麼。代碼在我的IDE中完美運行,但是顯示上述在使用GCC的Ubuntu終端上運行的錯誤。在不同IDE上動態分配內存(基於結構)的程序運行方式不同

/* Implements an employee structure having name and company name 
and can take new employees, delete last employee and display entire list of employees */ 

#include <stdio.h> 
#include <stdlib.h> 

// defining structure employee 
typedef struct emp 
{ 
    char name[20]; 
    char company[20]; 
}emp; 


int p = 0, size = 0; 

void create(emp *); 
void del(emp *); 
void display(emp *); 

int main(void) 
{ 
    emp *buffer = malloc(sizeof(emp)); 
    if (buffer == NULL) 
    { 
     printf("Error"); 
     exit(1); 
    } 
    int n = 0; 
    do 
    { 
     printf("The options are:\n"); 
     printf("1. Add employee\n"); 
     printf("2. Delete employee\n"); 
     printf("3. Display employee\n"); 
     printf("4. Exit\n"); 
     printf("Enter from 1 to 4:"); 
     scanf("%d",&n); 
     if (n == 1) 
     { 
      create(buffer); 
     } 
     else if (n == 2) 
     { 
      del(buffer); 
     } 
     else if (n == 3) 
     { 
      display(buffer); 
     } 
    }while(n != 4); 
    free(buffer); 
    return 0; 
} 

void create(emp *buffer) 
{ 
    size++; 
    if (p != 0) 
    { 
     buffer = realloc(buffer, size * sizeof(emp)); 
     if (buffer == NULL) 
     { 
      printf("Error"); 
      exit(1); 
     } 
    } 
    printf("Enter:"); 
    scanf("%s%s", (buffer + size - 1)->name, (buffer + size - 1)->company); 
    p++; 
} 

void del(emp *buffer) 
{ 
    // deletes only last node 
    size--; 
    buffer = realloc(buffer, size * sizeof(emp)); 
    if (buffer == NULL) 
    { 
     printf("Error"); 
     exit(1); 
    } 
} 

void display(emp *buffer) 
{ 
    int k = 0; 
    for (k = 1; k <= size; k++) 
    { 
     printf("Name:%s\n",(buffer + k - 1)->name); 
     printf("Company:%s\n",(buffer + k - 1)->company); 
    } 
} 

更新: 我的valgrind跑和正在以下,但無法理解正是我重新分配不當。

==3322== Invalid free()/delete/delete[]/realloc() 
==3322== at 0x4C2FD5F: realloc (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so) 
==3322== by 0x4008C9: create (in /home/akshay/Data/practice/a.out) 
==3322== by 0x40081C: main (in /home/akshay/Data/practice/a.out) 
==3322== Address 0x5203040 is 0 bytes inside a block of size 40 free'd 
==3322== at 0x4C2FD5F: realloc (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so) 
==3322== by 0x4008C9: create (in /home/akshay/Data/practice/a.out) 
==3322== by 0x40081C: main (in /home/akshay/Data/practice/a.out) 
==3322== Block was alloc'd at 
==3322== at 0x4C2DB8F: malloc (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so) 
==3322== by 0x400786: main (in /home/akshay/Data/practice/a.out) 
==3322== 
Error==3322== 
==3322== HEAP SUMMARY: 
==3322==  in use at exit: 80 bytes in 1 blocks 
==3322== total heap usage: 5 allocs, 4 frees, 2,288 bytes allocated 
==3322== 
==3322== LEAK SUMMARY: 
==3322== definitely lost: 80 bytes in 1 blocks 
==3322== indirectly lost: 0 bytes in 0 blocks 
==3322==  possibly lost: 0 bytes in 0 blocks 
==3322== still reachable: 0 bytes in 0 blocks 
==3322==   suppressed: 0 bytes in 0 blocks 
==3322== Rerun with --leak-check=full to see details of leaked memory 
==3322== 
==3322== For counts of detected and suppressed errors, rerun with: -v 
==3322== ERROR SUMMARY: 1 errors from 1 contexts (suppressed: 0 from 0) 
+0

發佈[MCVE]或使用調試器/清潔劑。 –

+0

可能是指向'buffer'的指針作爲參數......它們應該是指向指針的指針,例如:'void del(emp ** buffer)' – Toby

+0

@Toby但是,如何訪問指向指針的指針更改實際數據?此外,我得到的錯誤是雙重免費或腐敗。所以,它應該與釋放內存有關... – akshayk07

回答

2

你是按值傳遞緩衝區createdel所以無論你更改了它沒有被反映出來。因此free的舊值爲buffer。你有3個選項 -

O1:使緩衝區全局像你所做的大小,不要把它作爲參數傳遞。簡單但不建議。

O2:從delcreate返回buffer的新值。然後在調用的時候做

buffer = del(buffer); 

O3:傳遞指向緩衝區而不是緩衝區的指針並在裏面修改它。您的原型將變爲

void create(emp ** buffer); 

,你將不得不使用*buffer每一個地方內create(同爲del)。 另外通話將變爲

create(&buffer); 

這是一個有點複雜,但最「正確」的。

希望能幫助你理解問題。

+0

謝謝,這清除了我的懷疑。 – akshayk07