2012-09-27 59 views
0

我有一個內存分配問題。如果我在else塊中聲明char*,這意味着else塊完成執行時char*被銷燬。 else塊位於while循環中,因此它將迭代多次。但是,如果在else塊中聲明的char*變爲別名爲malloc'd變量,如下例所示:我的問題是,我如何收費?我覺得如果我釋放臨時變量char*,我將導致分段錯誤,因爲我將釋放我想保留的變量。如果是這樣的話,那麼我就不知道free聲明的用處。內存分配C

char* print_path = NULL; 

(SNIP)

(while) 

else{ 
     char* temp_path = print_path; 
     int temp_size = strlen(temp_path)+strlen(file_name(child->fts_path))+1; 
     print_path = (char*)malloc(temp_size); 
     strcpy(print_path, temp_path); 
     strncat(print_path, file_name(child->fts_path), strlen(file_name(child->fts_path))); 
     printf("%s:\n\n", print_path); 
     } 

(中略)

我想指出的是,我做免費print_path在節目結束後,我知道它不會被再次執行。然而,這是我想要釋放的循環的中間執行。任何幫助,將不勝感激。 謝謝!

+2

你混淆了堆棧分配和堆分配的東西。你沒有釋放指針,你釋放了指針指向的內存。 –

+0

在循環的每次迭代中釋放點有什麼意義?你知道在循環期間你將需要這段內存,釋放和重新分配在這裏沒有多大意義。 –

+0

@JordanKaye在每次迭代期間釋放的一點是因爲之前迭代的動態分配變量不再需要。如果這是通過足夠長的數據採樣運行的,則不會留下任何內存。當不再需要時,釋放所有malloc'd變量也是很好的編程實踐。 – tpar44

回答

2

看起來像free(temp_path)是正確的。它應該是這樣的:

char * print_path = malloc(...); // "NULL" is also possible 

while (condition) 
{ 
    if (...) 
    { 
     // ... 
    } 
    else 
    { 
     char * temp_path = print_path; 

     print_path = malloc(...); 

     free(temp_path); 
    } 
} 

free(print_path); 

在你的算法是不變的(或者應該是)該print_path總是指向動態mallo ­ cated內存。請注意,我們每隻有一個free

+0

是的,那是我最初擁有'free(temp_path)'語句的地方,但是我遇到了分段錯誤,但我認爲我可能一直在做一些錯誤的事情,因爲我幾乎肯定「免費」應該是去那裏。難道temp_path實際上不是一個動態分配的內存塊嗎? – tpar44

0

你有2個指針:

print_paths:點像['h','e','l','l','o']一個數組,這個指針包含的地址爲數組的第一個元素,在這種情況下,它指向h,讓說的這個地址h1,因此,e的地址是2等等......因此,print_path包含數字1

temp_path:這個指針指向什麼也沒有指向內存中的隨機位置。

當你呼叫malloc,malloc要求一些內存,並給你新的分配內存的地址,但這個內存包含垃圾。

所以經過

print_path = (char*)malloc(temp_size); 

print_path包含新分配的內存的地址,大小temp_size其中有垃圾的一個新的數組,可以說,這個地址是40,所以print_path40

最後,當你撥打:

strcpy(print_path, temp_path); 

你的陣列temp_path['h','e','l','l','o'])的值複製到由print_path指向的陣列,換句話說,地址40而不是包含垃圾現在包含h41包含e等。

重要的是要注意,即使兩個地址(140)都包含值h,修改一個也不會影響另一個。

free(temp_path)最好的地方僅僅是else結束前,剛剛檢查temp_path分配內存,如果你嘗試在未與malloc傻冒獲得免費存儲要去有不好的時候。

+0

謝謝,但在發佈之前我曾嘗試過,因爲當我將它放在那裏時出現了分段錯誤。難道是因爲'temp_path'是'print_path'的副本而不是動態分配的? – tpar44

+0

@ tpar44可能是因爲你的第一個'print_path'是'NULL',你試圖釋放一個'NULL'指針嗎?嘗試類似於這樣的方法 if(temp_path!= NULL) free(temp_path);' if你的第一個'print_path'不是'NULL'指針,可能你正在分配'temp_path',就像'temp_path = child-> fts_path',也就是你正在分配'temp_path'內存,你會稍後使用,所以,你可以在代碼的這一部分中釋放它,並且稍後嘗試訪問它 –

0

我認爲,因爲我想要做的重點是將內存重新分配給相同的變量,我應該看看realloc而不是malloc。