2016-02-09 52 views
2

我得到了內存泄漏,當我創建的雙A 50'000值向量,我不知道爲什麼。內存泄漏的std ::矢量管理C++

#include <stdafx.h> 
#include <Windows.h> 
#include <psapi.h> 

#define MEMLOGINIT double mem1, mem2;\ 
        PROCESS_MEMORY_COUNTERS_EX pmc;\ 
        GetProcessMemoryInfo(GetCurrentProcess(), (PROCESS_MEMORY_COUNTERS*)&pmc, sizeof(pmc));\ 
        SIZE_T virtualMemUsedByMe = pmc.PrivateUsage;\ 
        mem1 = virtualMemUsedByMe/1024.0;\ 
        std::cout << "1st measure \n Memory used : " << mem1 <<" Ko.\n\n";\ 

#define MEMLOG(stepName) GetProcessMemoryInfo(GetCurrentProcess(), (PROCESS_MEMORY_COUNTERS*)&pmc, sizeof(pmc));\ 
          virtualMemUsedByMe = pmc.PrivateUsage; \ 
          mem2 = virtualMemUsedByMe/1024.0; \ 
          std::cout << stepName << "\n Memory used : " << mem2 << " Ko.\n Difference with previous measure : " << mem2 - mem1 <<" Ko.\n\n";\ 
          mem1 = mem2; 



int _tmain(int argc, _TCHAR* argv[]) 
{ 
    MEMLOGINIT; 
    { 
     vector<double> spTestmemo(50000 ,100.0); 
     MEMLOG("measure before destruction"); 
    } 
    MEMLOG("measure after destruction"); 
}; 

output with 50k values 顯然這裏由矢量分配的400 KO不會釋放。

然而,析構函數可與500,000個值的向量。

int _tmain(int argc, _TCHAR* argv[]) 
{ 
    MEMLOGINIT; 
    { 
     //vector<double> spTestmemo(50000 ,100.0); 
     vector<double> spTestmemo(500000 ,100.0); //instead of the line above 
     MEMLOG("measure before destruction"); 
    } 
    MEMLOG("measure after destruction"); 
}; 

output with 500k values 這裏,大十倍比前一個幾乎完全破壞(4 KO小偏壓)的載體。

感謝您的幫助。

+0

您是否在啓用優化的情況下構建?這可能是編譯器或庫實現的一些優化。 –

+1

我懷疑你在這裏看到內存泄漏。我認爲正在發生的事情是內存塊低於某個特定點,所以操作系統不像第二個例子中那樣回收它。 – NathanOliver

+4

編譯器的堆管理器決定什麼內存回到操作系統。你的場景可能會被'new []/delete []'複製,而不僅僅是'std :: vector'。一般來說,除非該類直接使用OS API調用分配內存,否則不應該依賴OS調用和工具來決定C++類是否泄漏內存,而繞過編譯器的堆管理器。 – PaulMcKenzie

回答

2

由於NathanOlivier和PaulMcKenzie在他們的評論中指出,這不是一個內存泄漏。

了C++的std庫可能不釋放所有內存的操作系統,當你釋放它,但記憶仍在考慮。

所以不要太擔心你看到了什麼作爲OS報告程序的虛擬內存的使用,只要它不是高得離譜或在程序運行時不斷增加。

---開始Visual Studio的具體:

既然你似乎是建立與Visual Studio代碼,其調試運行時庫做你與你的MEMLOGINIT和MEMLOG宏做什麼設施,看到https://msdn.microsoft.com/en-us/library/974tc9t1.aspx#BKMK_Check_for_heap_integrity_and_memory_leaks

基本上,您可以使用_CrtMemCheckpoint獲取已分配內容的狀態,並使用_CrtMemDifference和_CrtMemDumpStastistics來比較並記錄2個檢查點之間的差異。

運行時庫的調試版本還自動轉儲內存泄露你的程序,當程序退出的調試器控制檯。如果將新定義爲DEBUG_NEW,它甚至會記錄每個泄漏分配的源文件和行號。尋找內存泄漏時,這通常非常有價值。