程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
 程式師世界 >> 編程語言 >> C語言 >> C++ >> C++入門知識 >> Effective C++ 10

Effective C++ 10

編輯:C++入門知識

Effective C++ 10


10.如果寫了operator new,就要同時寫operator delete。


為什麼要寫自己的operator new和delete,首先這不叫重載,這叫隱藏。 new只是用來申請空間,而構造函數是在申請的空間的基礎上繼續初始化。

為了效率。缺省的operator new 進行內存分配是並不僅僅分配一塊所需大小的內存,因為delete釋放內存時要知道指針所指向內容的大小,所以,new時會有一個塊來儲存內存塊的大小,而delete時,會根據這個大小來判斷刪除內存大小。所以當一個類本身很小的時候,這樣做,既浪費時間於內存大小的判斷,也浪費空間於內存大小的保存。對於某些類較小,且需要一定數量的這些小對象來儲存數據時,最好能寫一個operator new 來節約空間與時間。

而由於自己的Operator new申請的內存塊中沒有保存內存塊的大小,導致使用缺省的delete時,會導致不可預測的後果。所以若寫了operator new ,就必須同時寫operator delete。

一般解決方法是 申請一大塊內存,作為內存池,將其分為若干塊,每塊大小正好為儲存對象的大小。當前沒有被使用時。

嘗試將這種固定大小內存的分配器封裝起來。

//內存池的實現。
class Pool{
public:
	Pool (size_t n,int size);
	void* alloc(size_t n);//為一個對象分配足夠的內存
	void free(void* p,size_t n);//將p指定的內存返回到內存池。
	~Pool();//釋放內存池中的全部資源
private:
	void* block;
	const int BLOCK_SIZE;//池內存放塊的數量
	void* list;
};


Pool::Pool(size_t n,int size):BLOCK_SIZE(size){
	block = ::operator new(n*size);
	int i;
	for(i = 0;i

這是一個內存池的實現,結果感覺雖然實現了內存池的基本功能,但寫的不好看。。。譬如一些問題沒有解決,如果要求內存大於池的最大容量的處理,以及釋放池內元素時,如果重復釋放需要進行一些判斷此塊內存釋放已釋放。
忽略上面代碼,簡單分析一下內存池的基本功能:alloc 為對象申請空間的請求提供內存,而free釋放對象現在所在的內存。



這裡說的寫了 operator new 就要寫對應的operator delete,因為你在自己寫的new中一定會定義一些其他的操作,使的數據的組織結構不是一個簡單的new就實現的,可能有多塊動態地址,或者可能像內存池中並沒有實際的去申請新的空間,所以一定要根據自己寫的new中的操作,設計對應的delete操作。



  1. 上一頁:
  2. 下一頁:
Copyright © 程式師世界 All Rights Reserved