C++中運算子New的三種使用方式

來源:互聯網
上載者:User

轉自:http://badboywang.iteye.com/blog/446350
1. plain new 普通new

void*operator new(std::size_t)throw(std::bad_alloc);   void operator delete( void *) throw(); 

該運算子在分配失敗時將拋出異常,而非返回NULL。使用時要包含 <new>標頭檔。正常使用new,但要配以異常處理。如:

char *getMemory(unsigned long size)   {    char * p = new char[size];         return p; }   void main(void )   {    try{           char * p = getMemory(1000000);//可能發生異常           // ...           delete [ ] p;           }       catch(const std::bad_alloc & ex)       {  cout < <ex.what();    }   }

2.nothrow new  不拋擲異常new

void*operator new(std::size_t,const std::nothrow_t & )throw();   void operator delete( void *) throw();

該運算子在分配失敗時不拋出異常,而是返回NULL。使用時要包含 <new>標頭檔。 
該函數的第2形參是 struct nothrow_t {  };它是個全域常對象 const nothrow_t nothrow; 用來作為 new 運算子的標誌,以區別前一個new.
3.placement new 放置new

>void*operator new(std::size_t ,void *);   void operator delete( void * ,void *); 

該運算子是在已指派的記憶體上重新構造對象,因為不分配記憶體,所以不必擔心分配失敗。唯一的工作是調用建構函式。要包含 <new>標頭檔。

# include <new>   # include <iostream>   void main()   {  using namespace std;       char * p = new(nothrow) char [4];       if (p == NULL)       {  cout < <“allocte failed” < <endl;  exit( -1 );    }       // ...       long * q = new(p)long(1000);       delete [ ]p;    //只釋放 p,不要用q釋放。   } 

 p和q僅僅是首址相同,所構建的對象可以類型不同。所“放置”的空間應小於原空間,以防不測。當”放置new”超過了申請的範圍,Debug版下會掛機,但Release版竟然能運行而不出錯!
該運算子的作用是:只要第一次分配成功,不再擔心分配失敗。

# include <new>   # include <iostream>   void main()   {  using namespace std;       char * p = new(nothrow) char [100];       if (p == NULL)       {  cout < <“allocte failed” < <endl;  exit( -1 );    }       long * q1 = new(p)long(100);       // 使用q1  ...       int * q2 = new(p) int[100/sizeof(int) ];       // 使用q2 ...       ADT * q3 = new(p) ADT[100/sizeof(ADT) ];       // 使用q3  然後釋放對象 ...       delete [ ]p;    //只釋放空間,不再析構對象。   }

注意:使用該運算子構造的對象或數組,一定要顯式調用解構函式,不可用delete代替析構,因為placement new 的對象的大小不再與原空間相同。

# include <new>   # include <iostream>   void main()   {  using namespace std;       char * p = new(nothrow) char [sizeof(ADT)+2];       if (p == NULL)       {  cout < <“allocte failed” < <endl;  exit( -1 );    }       // ...       ADT * q = new(p) ADT;       // ...       // delete q;    // 錯誤       q-> ADT::~ADT(); //顯式調用解構函式,僅釋放對象       delete [ ]p;    //最後,再用原指標來釋放記憶體.   } 

 placement new 的主要用途就是可以反覆使用一塊已申請成功的記憶體空間。這樣可以避免申請失敗的徒勞,又可以避免使用後的釋放。 

    特別要注意的是對於 placement new 絕不可以調用的delete, 因為該new只是使用別人替它申請的地方(只是個租房戶,不是房主。無權將房子賣掉)。釋放記憶體是nothrow new的事,即要使用原來的指標釋放記憶體

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.