之前在看C++書和上C++課的時候能夠看到數組
delete[] pointer;
的用法,而大多數對於這個用法沒有具體的解釋,可能是看到:函數
有一個delete運算符的特殊語法,能夠釋放動態分配的數組內存:操作系統
delete[] p_numbers;方括號告訴編譯器,指針指向了一個數組,而不是單個值。設計
引文自:《C++程序設計:現代方法》,14.2 指針和數組指針
也沒有說明若是缺乏[]
會帶來的後果,猜測是內存泄露,可是不明就裏,因而給我來帶了C++內存管理詭譎的印象。不過最近侯捷先生的講解卻非常清晰。調試
下方所說Complex類爲僅包含兩個double類型成員,String僅含一個char類型指針。code
首先說的是構造,以Complex類爲例:對象
Complex *c = new Complex(1,2);
執行過程爲:blog
Complex *c; void* mem = operator new( sizeof(Complex) ); //內部調用malloc(n),分配內存 c = static_cast<Complex*>(mem); //類型轉換 c->Complex::Complex(1,2); //→Complex::Complex(c,1,2),構造函數
那麼在內存中執行的時候分配內存爲:內存
紅色部分爲操做系統分配之Cookie,藍色部分爲填充位,目的是爲了讓整個長度爲16的倍數。灰色區域內數據僅在Debug模式下出現,綠色區域爲對象所佔長度。可計算,Debug模式下的Complex實例長度爲:
8[兩個雙精度浮點實數] + (32+4)[調試模式] + (4×2)[Cookie] → 52 + 12[填充] → 40H
那麼此時向操做系統取內存時Cookie末位置1,即Cookie爲00000041
,釋放時末位置0。之因此保持16(10H)的倍數即如此。
Release下的String類型長度則爲:
4[指針] + (4×2)[Cookie] → 12 + 4[填充] → 10H
執行
String *s = new String(1,2); … delete s;
到delete s
的時候會:
String::~String(s); //析構函數 operator delete(s); //釋放內存,其內部調用free(s)
即執行String類析構函數後釋放內存,釋放Cookie標記段。看起來彷佛沒什麼問題。
看一下
Complex *c = new Complex [3];
和
String *s = new String [3];
的內存結構,能夠發現是這樣的:
在頂部多存儲了一個數組長度。那麼執行delete
和delete[]
有什麼區別呢?是這樣的:
能夠看到,對於內存而言,delete
必定會將Cookie標記段給釋放掉,若是是相似Complex的數組,那麼使用delete
與delete[]
的效果是一致的,可是針對String這類含指針類型的數組,使用delete
僅執行首次析構,也就是在這裏出現了內存泄漏。
最近怎麼關心內存泄漏了?
程序跑了一夜泄漏了8G內存,不關心一下怎麼得了。