1 若是出於某些緣由,須要在const成員函數中修改某一個或幾個成員,那麼能夠將須要修改的成員聲明爲mutable,例如函數
class A { public: int m_cannotBeModified; mutable int m_needToBeModified; void ModifyMutable() const { m_needToBeModified = 1; //合法 m_cannotBeModified = 1; //不合法 } };
2 若是一個類沒有顯式聲明構造函數,拷貝構造函數,賦值運算符,析構函數,編譯器會相應地合成一個,若是類顯式定 義了任何一個構造函數,包括拷貝構造函數,編譯器就不會再合成構造函數。
3 要阻止一個類對象拷貝或賦值,能夠聲明一個簡單的基類,基類中將拷貝構造函數和賦值運算符聲明爲private,這樣其派生類的拷貝或賦值操做在編譯期就能夠被檢查出來。例如:this
class A { protected: A(){} ~A(){} private: A(const A& a){} A& operator=(const A&a){} }; class B : public A { }; int main() { B b; //B b1(b); //編譯不經過 //B b2 = b; //編譯不經過 B b3; //b3 = b; //編譯不經過 return 0; }
若是B不繼承自任何類,直接把其拷貝構造函數和賦值運算符聲明爲private,並定義,那麼類外不能作拷貝或賦值操做, 類內部或友元函數或友元類仍可作拷貝或賦值操做。
若是B不繼承自任何類,直接把其拷貝構造函數和賦值運算符聲明爲private,不提供定義,那麼類外不能作拷貝或賦值操做,類內部或友元函數或友元類要作拷貝或賦值操做的話,連接期會發現錯誤,由於沒有提供定義。
4 若是在基類的構造函數中調用虛函數,那麼虛函數毫不會降低到派生類階層,調用的還是基類自己的虛函數,這時虛函數並無表現得像虛函數。派生類對象在基類構造期間,其對象類型就是基類,其運行時類型信息也屬於基類,在進入派生類構造函數前毫不會成一個派生類對象。
5 使用引用計數型智能指針shared_ptr能夠有效管理資源,但若是使用shared_ptr時出現了環狀引用,仍是會致使內存泄露例以下面的代碼,程序退出後,new出來的A和new出來的B的引用計數都仍然是1,堆上的內存空間都不會釋放。指針
class B; class A { public: shared_ptr<B> m_b; }; class B { public: shared_ptr<A> m_a; }; int main() { shared_ptr<A> a(new A); //new出來的A的引用計數此時爲1 shared_ptr<B> b(new B); //new出來的B的引用計數此時爲1 a->m_b = b; //B的引用計數增長爲2 b->m_a = a; //A的引用計數增長爲2 }
再例以下面的代碼,主函數退出後,new出來的CCycleRef引用計數爲1,內存沒法釋放:code
class CCycleRef { public: ~CCycleRef() { cout <<"destroying CCycleRef"<<endl; } public: shared_ptr<CCycleRef> selfRef; }; void CycleRefTest() { shared_ptr<CCycleRef> cyclRef(new CCycleRef()); cyclRef->selfRef = cyclRef; } int _tmain(int argc, _TCHAR* argv[]) { CycleRefTest(); return 0; }
解決辦法是使用弱智能指針定義類中的智能指針成員,即將類中的shared_ptr換成weak_ptr便可。
6 前置自增運算符返回的是操做數加1後的值,返回的是操做數自己,是一個左值後置自增運算符返回的是操做數加1前的值,其操做數能夠理解爲值與原操做數相等的一個常量,是一個右值。
重載前自增運算符和後自增運算符時,要保證其語義與全局的前自增運算符和後自增運算符的語義相同,即前自增返回一個左值,後自增返回一個右值。因此重載的前自增運算符一般返回該對象的引用,以支持++++obj這樣的操做;重載的後自增運算符一般返回該類的一個常量對象,防止出現obj++++這樣的操做。
例以下面的代碼:對象
class A { public: A(){ m_num = 0; } A& operator++() { ++m_num; return *this; } const A operator++(int i) { A temp(*this); ++*this; return temp; } public: int m_num; };