在c++中,有時我們需要在運行階段為一個變量分配未命名的內存,並使用指針來訪問它,這里就可以用到new關鍵字。另外需要指出的是,new分配的內存塊通常與常規變量分配的內存塊不同,常規變量的值都儲存在被稱為棧的內存區域中,而new從被稱為堆或自由儲存區的內存區域分配內存。new關鍵字還可以用於創建動態數組。c式創建數組是在編譯時為數組分配內存的,稱為靜態聯編,也就是數組是在編譯時載入到程序中的。但使用new時可以在運行時創建數組,稱為動態聯編,也就是數組是在程序運行時創建的。
當然,內存使用完后,可以使用delete釋放內存,將其歸還給內存池。(例如:int *ps =new int;.....delete ps;)這將釋放ps指向的內存,但不會刪除指針ps本身,ps還可以繼續使用。注意:不要嘗試釋放已經釋放的內存塊,c++表追指出,這樣做的結果將是不確定的。
new原型:void* __CRTDECL operator new(size_t _Size);
void* __CRTDECL operator new(size_t _Size,std::nothrow_t const&) throw();
delete原型:void __CRTDECL operator delete(void* _Block,size_t _Size) throw();
void __CRTDECL operator delete[](void* _Block,size_t _Size) throw();
當然,new/delete也是可以重載的。代碼如下:
void* arr[100]; static int num = 0; void * operator new[](size_t count) throw(std::bad_alloc) { printf_s("new[], 總大小為:\t%d\n", count); return (operator new(count)); } void* operator new(size_t size) throw(std::bad_alloc) { printf_s("new:\t%d Byte\n",size); void* m = malloc(size); if (!m) puts("out of memory"); printf_s("new @:\t0x%0x\n", (int*)m); arr[num++] = m; return m; } //重載delete,要加__CRTDECL,否則不讓重載 void __CRTDECL operator delete(void* m) throw(std::bad_alloc) { printf("delete @:\t0x%0x\n", (int*)m); for (int i = 0; i < num; ++i) { if (0 == (int*)m - (int*)arr[i]) { arr[i] = NULL; break; } } free(m); }
注意: 若代碼用vs編寫則需要做些修改:Project->Settings->Link頁,然后在Project Options的Edit欄中輸入/verbose:lib即可。
(防止出現錯誤 LNK2005 "void __cdecl operator delete(void *)" (??3@YAXPAX@Z) 已經在 MSVCRTD.lib(delete_scalar.obj) 中定義)。