More Effective C++讀書筆記(二)

來源:互聯網
上載者:User

1、不要試圖重載||,&&操作符,因為它們使用短路求值法(一旦確定了布林運算式的真假值,即使還有部分運算式沒有被測試,布林運算式也停止運算),而重載之後採用的是函數調用法。首先當函數被調用時,需要運算其所有參數,所以調用函數functions operator&& 和 operator||時,兩個參數都需要計算,換言之,沒有採用短路計演算法。第二是C++語言規範沒有定義函數參數的計算順序,所以沒有辦法知道運算式1與運算式2哪一個先計算。完全可能與具有從左參數到右參數計算順序的短路計演算法相反。同樣,也不要試圖重載逗號(,)操作符,因為一個包含逗號的運算式首先計算逗號左邊的運算式,然後計算逗號右邊的運算式,整個運算式的結果是逗號右邊運算式的值,這也可能和函數調用法對參數的計算順序不同。因為重載操作符很重要的一點就是要重載之後行為特性與其被料想(預設的行為特徵)的一樣。否則,重載是完全輕率的行為。C++規定不能重載的操作符有., .*, ::, ?:,new, delete, sizeof, typeid,static_cast, dynamic_cast, const_cast, reinterpret_cast

2、理解各種不同含義的new和delete(new操作符和operator new操作),先分析一段代碼:
string *ps = new string("Memory Management");
使用的new是new操作符。這個操作符就象sizeof一樣是語言內建的,你不能改變它的含義,它的功能總是一樣的。
它要完成的功能分成兩部分:第一部分是分配足夠的記憶體以便容納所需類型的對象。第二部分是它調用建構函式初始化記憶體中的對象。new操作符總是做這兩件事情,你不能以任何方式改變它的行為(不能重載)。
完成new操作符功能的第一部分分配記憶體所調用函數的名字是operator new(可以重載)。
函數operator new 通常這樣聲明:
void * operator new(size_t size);
傳回值類型是void*,因為這個函數返回一個未經處理(raw)的指標,未初始化的記憶體。參數size_t確定分配多少記憶體。你能增加額外的參數重載函數operator new,但是第一個參數類型必須是size_t。operator new的職責只是分配記憶體(返回一個void *指標,有點類似C語言的malloc)。它對建構函式一無所知。
當你的編譯器遇見這樣的語句:
string *ps = new string("Memory Management");
它產生的程式碼或多或少與下面的代碼(偽碼)相似:
void *memory = operator new(sizeof(string)); // 得到未經處理的記憶體
call string::string("Memory Management") on *memory;// 為String對象初始化
string *ps = static_cast<string*>(memory); //記憶體中的對象是ps指標指向新的對象

同樣,我們分析定位new操作符,例如:
new (buffer) Widget(widgetSize)
當該定位new操作符隱含調用operator new函數時,把這個變數(記憶體位址buffer)傳遞給它。被調用的operator new函數除了待有強制的參數size_t外,還必須接受void*指標參數,指向構造對象佔用的記憶體空間。這個operator new就是placement new,它看上去象這樣:
void * operator new(size_t, void *location)
{
return location;
}
總結:
如果想在堆上建立一個對象,應該用new操作符。它既分配記憶體又為對象調用建構函式。如果你僅僅想分配記憶體,就應該調用operator new函數;它不會調用建構函式。如果你想定製自己的在堆對象被建立時的記憶體配置過程,你應該寫你自己的operator new函數,然後使用new操作符,new操作符會調用你定製的operator new。如果你想在一塊已經獲得指標的記憶體裡建立一個對象,應該用placement new。

對於delete和operator delete也有類似的結論:
delete 先調用解構函式,然後調用operator delete釋放記憶體,而operator delete僅僅是釋放記憶體。如果你用placement new在記憶體中建立對象,你應該避免在該記憶體中用delete操作符。因為delete操作符調用operator delete來釋放記憶體,但是包含對象的記憶體最初不是被operator new分配的,placement new只是返迴轉遞給它的指標。誰知道這個指標來自何方?而你應該顯式調用對象的解構函式來解除建構函式的影響。

本文來自CSDN部落格,轉載請標明出處:http://blog.csdn.net/digu/archive/2007/11/13/1882023.aspx

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在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.