c++的動態物件建立
當建立乙個c++
物件時,會發生兩件事:
(1)為物件分配記憶體
(2)呼叫建構函式來初始化那個記憶體
然而,為物件分配記憶體可以用以下幾種方式或在可選擇的時間發生:
(1)在靜態儲存區域,儲存空間在程式開始之前就可以分配。這個儲存空間在整個執行期間都存在。
(2)無論何時到達乙個特殊的執行點(左大括號)時,儲存單元都可以在棧上被建立。出了執行點(右大括號),這個儲存單元自動被釋放。這些棧分配運算內置於處理器的指令集中,非常有效。但是,在寫程式的時候,必須知道需要多少個儲存單元,以便編譯器知道生成正確的指令。
(3)儲存單元也可以從一塊稱為堆的地方分配。這被稱為動態記憶體分配。在執行時呼叫程式分配這些記憶體。這就意味著在任何時候可以分配記憶體以及分配多少記憶體,當然也需要負責決定何時釋放記憶體。
為了在執行時動態分配記憶體,c
在它的標準庫函式中提供了一些函式:從堆中申請記憶體的函式
malloc()
以及它的變種
calloc()
和realloc()
、釋放記憶體返回給堆的函式
free()
。下面我們看乙個例子:
1 #include2 #include3 #include4 #include5 #include6 #include7#define inf 0x7fffffff
8using
namespace
std;910
class
obj11
18void destroy() const
21private:22
inti, j, k;
23enum ;
24char
buf[sz];
25};
2627
intmain()
28
程式中有這樣一行**,使用了malloc()
為物件分配記憶體:
1 obj* obj = (obj*)malloc(sizeof(obj));
這裡使用者必須決定物件的長度,由於malloc()
只是分配了一塊記憶體而不是生成乙個物件,所以它返回了乙個
void*
型別指標。而
c++裡面不允許將乙個
void*
指標賦予任何其他指標,所以必須做型別轉換。
使用者在使用物件之前必須記得對它初始化。注意建構函式沒有被使用,這是因為建構函式不能被顯示地呼叫
---它是在物件建立時由編譯器呼叫。
許多程式設計者發現c
的動態記憶體分配函式太複雜,容易令人混淆。所以,
c程式設計者常常在靜態記憶體區域使用虛擬記憶體機制分配很大的變數陣列以避免使用動態記憶體分配。為了在
c++中使得一般的程式設計師可以安全使用庫函式而不費力,所以沒有接受
c的動態記憶體分配方法。
c++中的解決方法是把建立乙個物件所需的所有動作都結合在乙個稱為
new的運算子裡。我們當用
new(
new
的表示式)建立乙個物件時,它就在堆裡為物件分配記憶體並為這塊記憶體呼叫建構函式。我們可以為類使用任何可用的建構函式而寫乙個
new表示式,如果建構函式沒有引數,可以寫沒有建構函式參數列的
new表示式。
new表示式的反面是
delete
表示式。
delete
表示式首先呼叫析構函式,然後釋放記憶體。如果正在刪除的物件的指標是
0,將不發生任何事情。為此,我們經常建議在刪除指標後立即把指標賦值為
0以免對它刪除兩次,從而產生某些問題。
1#ifndef tree_h
2#define tree_h
3 #include
4using
namespace
std;56
class
tree
710 ~tree()
11 friend ostream& operator
<< (ostream& os, const tree*t)
14private:15
intheight;
16};
1718
#endif
//tree_h
1 #include "tree.h"2
using
namespace
std;34
intmain()
5
當使用new
在堆上建立物件陣列時,如下面這一行**:
mytype* fp = new mytype[100];
這樣在堆上為100
個mytype
物件分配了足夠的記憶體並為每乙個物件呼叫了建構函式。銷毀這個陣列時我們應該這樣寫:
delete fp;
空的方括號告訴編譯器產生**,該**的任務是將從陣列建立時存放在某處的物件數量取回,並為陣列的所有物件呼叫析構函式。
當operator new()
找不到足夠大的連續記憶體塊來安排物件時,將會發生什麼事情呢?乙個稱為
new-handler
的特殊函式將會被呼叫。首先,檢查指向函式的指標,如果指標非
0,那麼它指向的函式將被呼叫。
1 #include2 #include3 #include4 #include5 #include6 #include7 #include8#define inf 0x7fffffff
9using
namespace
std;
1011
int cnt = 0;12
13void
out_of_memory()
1418
19int
main()
2026
return0;
27 }
說明:new-handler
函式必須不帶引數且其返回值為
void
。while
迴圈將持續分配
int物件直到空的記憶體被耗盡。在緊接下去的下一次對
new的呼叫時,將沒有記憶體可被呼叫,所有呼叫了
new-handler
函式。new-handler函式試著呼叫
operator new()
,如果已經過載了
operator new()
,則new-handler
將不會按預設呼叫。所以如果我們仍想呼叫
new-handler
,那麼我們不得不在過載的
operator new()
的**裡加上做這些工作的**。
和delete
。
MFC動態建立物件
define implement dyncreate class name,base class name cobject pascal class name createobject implement runtimeclass class name,base class name,0xffff,...
動態建立dom物件
在我們實際的專案之中,相信有很多的朋友直接使用了以下的格式建立dom元素 而且用的應該是還是樂此不疲,但是有多少人知道這是錯誤的做法 錯誤的原因 1 在頁面載入時改變了頁面的結構.在ie6中如果網路變慢或者頁面內容太大就會出現 終止操作 的錯誤.也就是說 永遠不要在頁面載入時改變頁面的dom模型 2...
C C 動態建立物件
一.用new和delete申請記憶體 在c 中用new和delete代替malloc和free 申請乙個物件 int p new int 釋放 delete p 注意 1 new的返回值就是物件指標,不用再轉換了 2 new的時候可以設定初值 new int 12 申請多個物件 int p new ...