網頁

2013年5月10日 星期五

C++ operator new/delete

Last Update: 2013/05/10 17:50+08


Intro

Operator new/delete 的測試
先說明一下 new 和 delete 的行為, 如下
MyClass* test = new MyClass();
/*Operator new(sizeof(MyClass)) => exec constructor*/
delete test
/*exec destructor => free(test)*/


Content


建立咱們的測試class
class MyClass{
public:
 int a;
 MyClass(){ printf("constructor \n"); }
 MyClass(int val){ printf("constructor-%i \n",val); }
 ~MyClass(){ printf("destructor \n"); }
};


咱們先來看一下, operator new/delete 的行為
 MyClass* mc1 = (MyClass*) ::operator new (sizeof(MyClass));
 ::operator delete(mc1);
沒有執行建構子
也沒有執行解構子



 MyClass* mc2 = new MyClass();//constructor
 delete mc2;//destructor
基本型, 分配memory -> 執行建構子
執行解構子 -> 釋放memory



 //just like: new MyClass(30)
 MyClass *mc3 = new(MyClass)(30);//constructor-30
 free(mc2); //no run destructor
這個跟上面(mc2)是一樣的行為
另外是, 若只執行free是不會執行解構子



 MyClass* mc4 = (MyClass*) malloc(sizeof(MyClass));
 int* temp = (int*)mc4;
 temp[0] = 99;
 printf("%i \n", mc4->a);//print 99
 free(mc4);
這裡不會執行建構子和解構子
與operator new/delete相同 (同mc1)
事實上, 你分配了一塊memory
你愛怎麼用 是你家的事 囧rz



-------------------------------
OK, 如果你使用了下述的statement
#include <iostream>
using namespace std;
你可以得到更多方便的操作



MyClass* mc5 = new (std::nothrow) MyClass(50);//constructor-50
delete mc5;//destructor
這個語句是在執行 new 失敗時, 不會有exception, 而是return NULL
後面代表你要執行的建構子



最後來模擬基本型的操作(like mc2)
 void* mc6Addr = ::operator new(sizeof(MyClass));
 MyClass* mc6 = new (mc6Addr) MyClass(60);
 printf("%lu %lu \n",mc6Addr, mc6);
 mc6->~MyClass();
 ::operator delete(mc6Addr);
line1, 新增(分配)memory
line2, 在 mc6Addr 所指向的 memory 上, 執行 MyClass 建構子 (note: 不需要cast)
      new (mc6Addr) 似乎被稱為 Placement
line3, 它們事實上是指向同一塊memory
line4, 執行解構子
line5, 刪除(釋放)memory



Reference

operator new - C++ reference

沒有留言:

張貼留言