2017-08-11 69 views
0

示例代碼是這樣的:任何方式都可以識別內存地址是否可用?

#include <iostream> 

using namespace std; 

int main() 
{ 
    int* addr = (int*)malloc(100); 
    cout << "Hello World" << endl; 
    printf("addr#1=%p\n",addr); 
    free(addr); 
    printf("addr#2=%p\n",addr); 

    return 0; 
} 

我知道addr#1addr#2將打印相同的地址。 但是有沒有一種方法可以識別可以自由使用的地址?

有人說這是不可能的,除非你重新分配NULLnullptraddr來識別。好的,如果指針指向一個對象,並且該對象被刪除,結果是一樣的?

+1

可能的重複[如何檢查指針是否已在C中釋放?](https://stackoverflow.com/questions/8300853/how-to-check-if-a-pointer-is-freed-already -in-c) –

+0

好吧,如果指針指向一個對象,並且該對象被刪除,結果是一樣的? – naive231

+0

如果這是C(標記爲),'printf(「addr#2 =%p \ n」,addr);'調用*未定義行爲*試圖在'free(addr)'後面訪問'addr'。 –

回答

0

你可以自由包裝並始終注意初始化指針。

void myfree(void **ptr) 
{ 
    free(*ptr); 
    *ptr = NULL; 
} 

所以每個空閒都會賦值NULL。如果指針爲NULL,則可以檢入程序。這只是某種解決方法

+1

多次引用同一個內存位置如何? –

0

我知道addr#1和addr#2會打印相同的地址。但任何 的方式可以確定一個可以自由使用的地址嗎?

理想的方式,以確定是否由malloc分配一塊存儲器是將指針指向設定爲一塊的存儲器是NULL,包括所有其它指針,其可以潛在地指向原始塊的存儲器。

好的,如果指針指向一個對象,並且該對象被刪除,結果是一樣的?

只是因爲一塊內存被釋放並不意味着原來在那個內存位置會被瞬間擦除。你可以調用它,看看你原來的東西,一些隨機的東西,或者你的程序可能會崩潰;這是未定義的行爲。 當你說「刪除」時,我假設你意味着釋放先前分配的一塊內存。

有人說,除非你重新分配NULL或nullptr到地址來標識

有由kennytm一個有趣的答案通過的mcheck使用和mprobe這裏How to check if a pointer is freed already in C? 發現這是不可能的,其中這些功能鉤到malloc和對堆進行瓶坯常量檢查。你可以製作一系列檢查來確定一個變量是否已被釋放,但這些函數純粹用於調試,而傳遞分配的內存則是安全的方式。

0

我知道addr#1和addr#2會打印相同的地址。但是有什麼方法可以確定一個可以自由使用的地址?

不容易或便攜。這是特定於C運行時庫的行爲,因此完全取決於實現細節。此外,這是未定義的行爲(免費使用)。

例如,您需要使用堆檢查例程,如使用GCC的mprobe來查詢運行時的狀態。

有人說這是不可能的,除非你將NULL或nullptr重新分配給addr來標識它。

不,只會改變你的有關該特定內存使用或狀態的觀點。它根據實際擁有並管理此信息的運行時庫說明系統的狀態。

好的,如果指針指向一個對象,並且該對象被刪除,結果是一樣的?

是的,無論是指向對象的指針還是指向POD的指針(結果如您所示),結果都是一樣的。

傳統觀點認爲,如果您遵循一定的規則和最佳實踐來處理內存管理問題,那麼您絕對不應該擔心這類問題。

這整個問題是使用smart pointers的一個很好的激勵示例!然後整個問題就消失了。

相關問題