改善程序的55个具体做法
生活随笔
收集整理的這篇文章主要介紹了
改善程序的55个具体做法
小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
1、確定對象在使用之前被初始化
(1)為內置對象進行手工初始化(因為C++不保證初始化它們) (2)構造函數最好使用成員初始化列表,而不要在構造函數本體內使用賦值操作。2、一個空類會默認生成哪些函數?
defult構造函數、copy構造函數、(非虛的)析構函數、賦值運算操作符函數operator= 【注】什么情況下,賦值運算操作符函數operator=不會自動生成,或者生成的不能被編譯成功? ①如果生成的代碼不合法或者生成的代碼無意義時 ②如果父類將賦值運算操作符函數operator=聲明為“private”,則編譯器拒絕為子類生成賦值運算操作符函數operator=(因為編譯器為子類生成的賦值運算操作符函數operator=原本想可以處理父類成分)。【operator=運算符重載的格式】A& A::operator=(const A& rhs) //返回值類型是 --> 類的引用A& {return *this; //返回的是 --> this指針指向的對象*this}【處理自我賦值=的情況】在程序中,難免會遇到“隱式的自我賦值”的情況,會帶來不可預知的錯誤,因此處理“自我賦值”成為了必不可少的一步!(用下面的例子進行說明如何處理自我賦值) class Widget { public: Widget(int x=0): val(new int(x)) {} ~Widget() { delete val; } Widget(const Widget &rhs): val(new int(*rhs.val)) {} Widget& operator=(const Widget &rhs); //operator = void print() const { cout << *val << endl; } private: int *val; }; Widget& Widget::operator=(const Widget &rhs) { //錯誤版本delete val; val = new int(*rhs.val); return *this; } Widget& Widget::operator=(const Widget &rhs) { //改進版本1:雖然具有自我復制安全性,但是不具有異常安全性。 //如果 new int 拋出異常的時候,this->val 指向的就是一個已經刪除的intif(this == &rhs) return; delete val; val = new int(*rhs.val); return *this; } Widget& Widget::operator=(const Widget &rhs) { //改進版本2:異常安全性與自我復制安全性兼具int *pOld = val; //記住原先的valval = new int(*rhs.val); //令val指向*val的一個附件(副本)delete pOld; //刪除原先的valreturn *this; } Widget& Widget::operator=(const Widget &rhs) { //改進版本3:copy and swap 技術Widget temp(rhs); swap(temp); return *this; } Widget& Widget::operator=(Widget rhs) { //改進版本4:通過傳值來實現 copy and swap swap(rhs); return *this; } 【技巧】若不想使用編譯器自動生成的函數(copy構造、賦值運算符operator=),應該怎么做?-->將相應的成員函數顯示的聲明為private類型。3、虛析構函數
(帶有多態(tài)性質的)父類析構函數應該聲明為virtual析構函數,防止“局部銷毀”造成的內存泄漏。不作為父類的虛函數不要聲明為virtual(因為會占用更多的空間)4、
在構造函數和析構函數中,不要調用virtual,因為這種調用從來不會實現多態(tài)(為什么不會實現多態(tài)?——>分析父類子類對象構造、析構的順序和多態(tài)實現的原理)5、傳遞參數時,盡量以pass-by-reference-const替換pass-by-value。前者通常比較高效,并可以避免切割問題(注:該規(guī)則并不適用于內置類型、STL的迭代器和函數對象,對它們而言,pass-by-value往往比較合適)
例: bool validataStudent(const Student& s); void printNameAndDisplay(const Window& w);6、必須返回對象時,別忘想返回其reference
例如重載的*運算符: const A operator*(const A& A1,const A& A2) {return A(A1.value * A2.value); }7、protected并不比public更具有封裝性
8、盡量用non-member、non-frend函數替換member函數。
9、盡量少做轉型動作
總結
以上是生活随笔為你收集整理的改善程序的55个具体做法的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: C语言深度解剖
- 下一篇: 错误:返回局部变量数组名 \ 解决方案