2013-03-28 55 views
2

我正在關注一個用於管理IP地址的C++ msdn參考。示例中的內存分配使用malloc而不是new。這是我的理解,malloc不應該在C++中使用。我會如何將這些malloc轉換爲新的?如何用新的示例替換malloc

鏈接:MSDN REFERENCE

中的代碼問題:

MIB_IPADDRTABLE *pIPAddrTable; 
DWORD   dwSize = 0; 
DWORD   dwRetVal; 

pIPAddrTable = (MIB_IPADDRTABLE*) malloc(sizeof(MIB_IPADDRTABLE)); 

if (GetIpAddrTable(pIPAddrTable, &dwSize, 0) == ERROR_INSUFFICIENT_BUFFER) 
{ 
    free(pIPAddrTable); 
    pIPAddrTable = (MIB_IPADDRTABLE *) malloc (dwSize); 
} 

if ((dwRetVal = GetIpAddrTable(pIPAddrTable, &dwSize, 0)) != NO_ERROR) 
{ 
    printf("GetIpAddrTable call failed with %d\n", dwRetVal); 
} 

printf("IP Address:   %ld\n", pIPAddrTable->table[0].dwAddr); 
printf("IP Mask:   %ld\n", pIPAddrTable->table[0].dwMask); 
printf("IF Index:   %ld\n", pIPAddrTable->table[0].dwIndex); 
printf("Broadcast Addr:  %ld\n", pIPAddrTable->table[0].dwBCastAddr); 
printf("Re-assembly size: %ld\n", pIPAddrTable->table[0].dwReasmSize); 

if (pIPAddrTable) 
    free(pIPAddrTable); 
+1

。在_modern C++ _中應該使用[適當的RAII容器,比如'std :: vector'](http://stackoverflow.com/a/15690742/1629821),而不是使用'new []'。 –

回答

3

,因爲他們不初始化對象爲new,你會不會有新的表達取代malloc這些用途。相反,他們將指針傳遞給分配的內存到GetIpAddrTable,這似乎是做初始化。

但是,有一個malloc的C++版本,它只進行內存分配:operator new。我配對的線,他們的替代:

pIPAddrTable = (MIB_IPADDRTABLE*) malloc(sizeof(MIB_IPADDRTABLE)); 
pIPAddrTable = (MIB_IPADDRTABLE*) ::operator new(sizeof(MIB_IPADDRTABLE)); 

pIPAddrTable = (MIB_IPADDRTABLE *) malloc (dwSize); 
pIPAddrTable = (MIB_IPADDRTABLE*) ::operator new(dwSize); 

free的使用也將需要與釋放函數operator delete更換:

free(pIPAddrTable); 
::operator delete(pIPAddrTable); 
+0

would pIPAddrTable =(MIB_IPADDRTABLE *)= new char [dwSize];也工作?然後刪除[] pIPAddrTable; – Brad

3

如果你想重新寫原創C風格代碼使用現代C++,您應該使用 std::vector而不是new[](和malloc)。

std::vector非常方便,例如,它會自動釋放其存儲器由於其析構函數(也以拋出的異常的情況下),它可以被調整大小,等等

這是上面的代碼,它使用std::vector代替mallocnew[]的一例(見在進一步的細節代碼)評論:

#include <windows.h> 
#include <Iphlpapi.h> 
#include <stdio.h> 
#include <vector>  // for std::vector 

#pragma comment(lib, "iphlpapi.lib") 

int main() 
{ 
    // Use std::vector to dynamically allocate memory. 
    std::vector<BYTE> buffer(sizeof(MIB_IPADDRTABLE)); 
    MIB_IPADDRTABLE * pIPAddrTable = reinterpret_cast<MIB_IPADDRTABLE*>(&buffer[0]); 

    DWORD dwSize = 0;  
    if (GetIpAddrTable(pIPAddrTable, &dwSize, 0) == ERROR_INSUFFICIENT_BUFFER) 
    { 
     // Resize buffer to proper size 
     buffer.resize(dwSize);   

     // Buffer memory can be re-based after allocation, so update base pointer 
     pIPAddrTable = reinterpret_cast<MIB_IPADDRTABLE*>(&buffer[0]); 
    } 

    DWORD dwRetVal; 
    if ((dwRetVal = GetIpAddrTable(pIPAddrTable, &dwSize, 0)) != NO_ERROR) 
    { 
     printf("GetIpAddrTable call failed with %d\n", dwRetVal); 
    } 

    printf("IP Address:   %ld\n", pIPAddrTable->table[0].dwAddr); 
    printf("IP Mask:   %ld\n", pIPAddrTable->table[0].dwMask); 
    printf("IF Index:   %ld\n", pIPAddrTable->table[0].dwIndex); 
    printf("Broadcast Addr:  %ld\n", pIPAddrTable->table[0].dwBCastAddr); 
    printf("Re-assembly size: %ld\n", pIPAddrTable->table[0].dwReasmSize); 

    // 
    // No need to cleanup memory: 
    // std::vector destructor will do that for us automatically :) 
    //  
} 

(注意:printf()可以與std::cout取代,但它並不像使用std::vector代替mallocnew[]重要)