2013-06-29 73 views
0

BS:我已經測試過,下面的問題是VS2010特定的,在我對Mingw的測試中,矢量內存泄漏, printf(「%d \ n」,testV-> size )); 給我'10',這表明它是一個泄漏。爲什麼矢量指針的內存自動清零

在代碼象下面這樣:

class Test{ 
public: 
    std::vector<int> *num; 
    int *n; 
}; 

Test *t = new Test(); 
t->num = new std::vector<int>; 
t->num->assign(10,10); 
t->n = new int[20]; 
t->n[0] = 12345; 
int *testN = t->n; 
std::vector<int> *testV; 

testV = t->num; 
delete t; 

//I can print n's memory 
printf("%d\n", testN[0]); //get 12345, so memory leaked here. 

//I can't print num's memory; its size is 0. in release version, it's negative number. 
printf("%d\n", testV->size()); 

刪除to後,我看到內存NUM點被清除,在我VS10的環境中,我可以看到它的內存清理,「EE FE EE FE .. ..'。 但n的記憶保持不變。

在我看來,所有內存都來自關鍵字new,應該通過刪除來釋放,好吧,這裏num(向量)是 不是'刪除',而是自動清除。

我想知道矢量指針與其他指針不同嗎?

+1

指向矢量的指針並沒有不同。儘管你的調試器可能導致你相信,但你仍然必須在這個新的指針上調用delete。 – juanchopanza

+1

你的測試不會向任何初始值填充矢量,所以當然'testV-> size()'將爲0. – greatwolf

+0

對不起,我現在填充了它,它的大小是負數,所以我猜測內存是自動清潔?我只是困惑爲什麼它不是10了,如果這個內存泄漏,它應該保持不變? –

回答

2

調試運行時將覆蓋它用像eefe這樣的標記刪除的內存,以檢測諸如免費後使用的錯誤。發佈版本不會這樣做。

您可能只是誤讀了調試輸出。 vector *和int *內存將仍然存在。調試器可能只是試圖在向量上變得更聰明。

+0

我可以打印testN [0],所以test-> n泄漏。 但testV.size ()是一個負數,而不是20,所以我認爲這表明test-> num的內存被清空了? –

+0

是的,它是一個編譯器特定的事情。在Mingw上,事情是不同的,所以我不能依賴這個特性 –

+0

@RobertBean能夠'printf'的東西並不意味着它被泄露(或者它並沒有被刪除,它只是意味着你正在編寫破壞的代碼,它在刪除之後試圖訪問內存 – jalf

3

只有t的內存被釋放,會員numn指的是泄漏內存。

您的測試是錯誤的,因爲您刪除後無法檢查t,並且沒有其他方式可以訪問這些成員(如果發現泄漏)。

+0

我剛剛編輯了我的問題,我確實可以檢查內存。我原本是通過記憶窺探工具來做的,在vs2010中,alt + 6就是這樣做的。 現在,在我的新代碼中,我用另一個指針來檢查它們。它們的行爲與我在VS2010中描述的相同 –

+0

由於't-> n'沒有被釋放,所以在釋放't'後,內存分配將保持不變,是的。 't'內的指針被覆蓋(在調試版本中)。在「t」中使用任何內容後就是「未定義的行爲」,這意味着它可能無法按照您的預期工作 - 無論您期望如何。 –

+0

我也認爲t-> num(向量指針)會導致泄漏,但在我的測試中,它似乎不是泄漏,導致泄漏的內存被清除。 (我得到這個結論testV.size()是一個負數,而不是10,這是我分配給的矢量。 –

1

如果要正確地做到這一點,你需要delete [] t->n;delete t->num;你做delete t;之前 - 但一個比較正確的做法,採用面向對象的「正確」,是讓t的構造函數和析構函數處理內存分配並釋放了nnum - 因此,自動爲該類本身正確管理內存。

我還要指出,使用指向std::vector的指針很少正確 - 矢量本身不佔用太多空間,因此您可能應該使用std::vector<int> num;而不是指向它的指針。這也意味着num在析構函數中被自動銷燬而不需要任何額外的代碼。