int *pi = new int(5); 實際分解為:
編譯器生成類似:
int *pi;
if (pi = (int*)operator new(sizeof(int))) *pi = 5;
delete pi; 要求對空指針無操作,編譯器生成:
if (pi != 0) operator delete(pi);
注意:`delete` 後指針值不自動置零,後續使用屬於未定義行為。
Point3d *p = new Point3d;
// 轉換為:
Point3d *p;
if (p = (Point3d*)operator new(sizeof(Point3d)))
p->Point3d::Point3d(); // 調用構造函數
異常安全:構造拋出異常時,編譯器會調用 `operator delete` 釋放內存。
void* operator new(size_t size) {
if (size == 0) size = 1; // 保證返回唯一指針
void* p;
while (!(p = malloc(size))) {
if (new_handler) (*new_handler)();
else return 0; // 或拋 bad_alloc
}
return p;
}
void operator delete(void* p) {
if (p) free(p);
}
new T[n]:若 T 為 POD 類型(無構造/析構),僅調用 `operator new[](n*sizeof(T))`。T 有構造函數,調用內部 `vec_new` 循環構造每個元素,並記錄元素個數(cookie 或關聯表)供 `delete[]` 使用。delete[] p 必須匹配 new[],否則僅析構第一個元素導致內存洩漏。