Effective C++筆記:使用noncopyable禁止類的拷貝
如果某些事物是獨(dú)一無二的,那么其相應(yīng)的類就應(yīng)該禁止拷貝,也就是要使類的copy構(gòu)造函數(shù)和copy assignment操作符不起作用。比如說,地球就是獨(dú)一無二的,那么可以這么定義地球:
class?Earth?{ public: ??......//member函數(shù)或friend函數(shù) private: ??Earth(const?Earth&);//只聲明 ??Earth&?operator=(const?Earth&);//只聲明 };
? ? ? ?有了上述class 定義,當(dāng)客戶企圖拷貝Earth對象,編譯器會(huì)阻撓他。如果你不慎在member函數(shù)或friend函數(shù)之內(nèi)那么做,輪到連接器發(fā)出抱怨。但是一種更好的做法是將連接期錯(cuò)誤移至編譯期,畢竟愈早偵測出錯(cuò)誤愈好。此時(shí)可以專門設(shè)計(jì)一個(gè)阻止copying動(dòng)作的base class,如下所示:
class?noncopyable { protected: ??noncopyable()?{} ??~noncopyable()?{} private://?emphasize?the?following?members?are?private ??noncopyable(?const?noncopyable&?); ??noncopyable&?operator=(?const?noncopyable&?); };
? ? ? ?對于構(gòu)造函數(shù)為什么聲明成protected呢?首先肯定不能為private,不然無法構(gòu)造子類實(shí)例。如果為public,那么外部是可以創(chuàng)建noncopyable這么一個(gè)實(shí)例的,可是這個(gè)實(shí)例是完全沒有意義的,該類只有在被繼承之后才有意義。所以此處聲明為protected是非常恰當(dāng)合適的,既保證外部無法直接構(gòu)造一個(gè)無意義的noncopyable實(shí)例,又不影響構(gòu)造子類實(shí)例。
? ? ? ?現(xiàn)在,為了阻止Earth對象被拷貝,我們唯一需要做的就是繼承Uncopyable。當(dāng)然,此時(shí)Earth內(nèi)部不需要再聲明copy構(gòu)造函數(shù)和copy assignment操作符了。
class?Earth:private?noncopyable { ??...... };