2012-07-26 173 views
0

以下是在C中實現的一個堆棧結構。我需要編寫一個函數(而不是一個方法)來釋放一個現有的堆棧並免費在堆上分配給它的任何內存。 dispose(stack * s)函數接受一個指向將被丟棄的堆棧的指針。釋放分配給指針的內存vs釋放分配給指針指向的內存

typedef struct { 
    int allocatedLength; 
    int logicalLength; 
    int elementSize; 
    void *elems; 
} stack; 

如果我按如下方式實現dispose()函數,是否會導致某些內存永遠不會被釋放?

void dispose (stack *s) { 
    free (s->elems); 
} 

在上面的實現中,我只釋放分配給elems的內存,這甚至不在堆上。我們需要記住,元素是指向某物的指針。我們是不是應該釋放某些東西,而不是釋放分配給指針的內存?

回答

1

你誤會:free(p)免費爲p內存,但對於*p的記憶 - 也就是內存通過p指向。因此,你正確釋放你存儲在s->elems指針分配的內存,一切都很好。

如果真的有人說「釋放我有指針的內存」,那麼可以責怪所有爲這個用詞不明的人解釋「釋放指針」的人。

0

你將釋放所有東西取決於你是否動態地分配struct stack。如果你不動態分配它,你只需要釋放(動態分配的內存)elems指向。這正是你在做什麼free (s->elems);

0

如果你正在爲struct stack分配內存,那麼free()應該只用於struct。不是爲它的成員。這是一個示例程序,它爲整個結構分配內存。免費()應該做的結構指針s( )。

如果free (s->elems);被取消註釋並且free (s);被註釋,printf會打印分配的數據。結構的內存不會被釋放並導致內存泄漏。

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

typedef struct { 
    int allocatedLength; 
    int logicalLength; 
    int elementSize; 
    void *elems; 
} stack; 


void dispose (stack *s) { 
    //free (s->elems); 
    free (s); 
} 

int main() 
{ 

stack *p = malloc(sizeof(stack)); 

if(p == NULL) 
    { 
      printf("\n Memory Allocation Error\n"); 
      return 0; 
    } 

    p->allocatedLength = 10; 
    p->logicalLength = 20; 
    p->elementSize = 30; 

    dispose(p); 

    /* This printf is undefined behaviour if stack's ptr is freed. If the elem only freed, then it prints data */ 
    printf("\n allocatedLength: %d\nlogicalLength:%d\nelementSize:%d", p->allocatedLength, p->logicalLength, p->elementSize); 


return 0; 
}