前言
1.複製建構函式和過載賦值操作符的定義;
2.複製建構函式和過載賦值操作符的呼叫時機;
3.複製建構函式和過載賦值操作符的實現要點;
4.複製建構函式的一些細節。
複製建構函式和過載賦值操作符的定義
我們都知道,在c++中建立乙個類,這個類中肯定會包括建構函式、析構函式、複製建構函式和過載賦值操作;即使在你沒有明確定義的情況下,編譯器也會給你生成這樣的四個函式。例如以下類:
複製** **如下:
class ctest
;對於建構函式和析構函式不是今天總結的重點,今天的重點是複製建構函式和過載賦值操作。類的複製建構函式原型如下:
複製** **如下:
class_name(const class_name &src);
一般來說,如果我們沒有編寫複製建構函式,那麼編譯器會自動地替每乙個類建立乙個複製建構函式(也叫隱式複製建構函式);相反的,如果我們編寫了乙個複製建構函式(顯式的複製建構函式),那麼編譯器就不會建立它。
類的過載賦值操作符的原型如下:
複製** **如下:
void operator=(const class_name &);
過載賦值操作符是乙個特別的賦值運算子,通常是用來把已存在的物件指定給其它相同型別的物件。它是乙個特別的成員函式,如果我們沒有定義這個成員函式,那麼編譯器會自動地產生這個成員函式。編譯器產生的**是以單一成員進行物件複製的動作。
總結了複製建構函式和過載賦值操作符的定義,只是讓我們了解了它們,而沒有真正的深入它們。接下來,再仔細的總結一下它們的呼叫時機。關於它們的呼叫時機,我一直都沒有真正的明白過,所以這裡一定要好好的總結明白了。
複製建構函式和過載賦值操作符的呼叫時機
對複製建構函式和過載賦值操作符的呼叫總是發生在不經意間,它們不是經過我們顯式的去呼叫就被執行了。對於這種隱式呼叫的地方一定要多注意了,這也一般是有陷阱的地方。現在我就用實際的例子來進行驗證;例子如下:
複製** **如下:
#include
using namespace std;
class ctest
~ctest(){}
ctest(const ctest &test)
void operator=(const ctest &test)
void test(ctest test)
{}ctest test2()
void test3(ctest &test)
{}ctest &test4()
}; int main()
在**中都加入了注釋,這裡就不再做詳細的說明了。再次總結一下,如果物件在宣告的同時將另乙個已存在的物件賦給它,就會呼叫複製建構函式;如果物件已經存在了,然後再將另乙個已存在的物件賦給它,呼叫的就是過載賦值運算子了。這條規則很適用,希望大家能記住。
複製建構函式和過載賦值操作符的實現要點
在一般的情況下,編譯器給我們生成的預設的複製建構函式和過載賦值操作符就已經夠用了;但是在一些特別的時候,需要我們手動去實現自己的複製建構函式。
我們都知道,預設的複製建構函式和賦值運算子進行的都是」shallow copy」,只是簡單地複製字段,因此如果物件中含有動態分配的記憶體,就需要我們自己重寫複製建構函式或者過載賦值運算子來實現」deep copy」,確保資料的完整性和安全性。這也就是大家常常說的深拷貝與淺拷貝的問題。下面我就提供乙個比較簡單的例子來說明一下:
複製** **如下:
#includ程式設計客棧e
using namespace std;
const int maxsize = 260;
class ctest
~ctest()
}ctest(const ctest &test)
ctest& operator=(const ctest &test)
// please delete the memory, thisnobmobhdo maybe cause the memory leak
if (pvalue)
// malloc the new memory for the pvalue
pvalue = new wchar_t[maxsize];
memset(pvalue, 0, sizeof(wchar_t) * maxsize);
wcscpy_s(pvalue, maxsize, test.pvalue);
return *this;
}void print()
private:
wchar_t *pvalue; // the pointer points the memory};
int main()
特別是在實現過載賦值建構函式時需要多多的注意,在**中我也新增了注釋,大家可以認真的閱讀一下**,然後就懂了,如果不懂的就可以留言問我;當然了,如果我**理解錯了,也希望大家能給我提出,我們共同進步。
複製建構函式的一些細節
1.以下哪些是複製建構函式
複製** **如下:
x::x(const x&);
x::x(x);
x::x(x&, int a=1);
x::x(x&, int a=1, int b=2);
這些細節問題在這裡也說一說,我也是從別人的部落格裡看到的,這裡自己也總結一下。對於乙個類x, 如果乙個建構函式的第乙個引數是下列之一:
複製** **如下:
a) x&
b) const x&
c) volatile x&
d) const volatile x&
且沒有其他引數或其他引數都有預設值,那麼這個函式是拷貝建構函式。
複製** **如下:
x::x(const x&); //是拷貝建構函式
x::x(x&, int=1); //是拷貝建構函式
x::x(x&, int a=1, int b=2); //當然也是拷貝建構函式
2.類中可以存在超過乙個拷貝建構函式
複製** **如下:
class x
;注意,如果乙個類中只存在乙個引數為 x& 的拷貝建構函式,那麼就不能使用const x或volatile x的物件實行拷貝初始化。如果乙個類中沒有定義拷貝建構函式,那麼編譯器會自動產生乙個預設的拷貝建構函式。這個預設的引數可能為 x::x(const x&)或 x::x(x&),由編譯器根據上下文決定選擇哪乙個。在我的visual studio 2012中,當定義了多個複製建構函式以後,編譯器就會有warning,但是程式還能正確執行。
總結這篇文章對複製建構函式和過載賦值操作符進行了一些總結,重點是在複製建構函式與過載賦值操作符的呼叫時機上;對於大家喜歡總結的深拷貝與淺拷貝問題,我沒有用過多的文字進行說明,我認為上面的**就足以說明問題了。最後自己糾結已久的問題也就這樣總結了,自己也徹底的明白了。
本文標題: c++中複製建構函式和過載賦值操作符總結
本文位址: /ruanjian/c/114635.html
C 複製建構函式與過載賦值操作符
c 拷貝建構函式 深拷貝,淺拷貝 c 中複製建構函式與過載賦值操作符總結 深拷貝和淺拷貝的區別 對深拷貝與淺拷貝的再次理解 禁止使用類的copy建構函式和賦值操作符 拷貝建構函式中的陷阱 在c 中建立乙個類,這個類中肯定會包括建構函式 析構函式 複製建構函式和過載賦值操作。複製建構函式是一種特殊的建...
C 中複製建構函式與過載賦值操作符總結
前言 這篇文章將對c 中複製建構函式和過載賦值操作符進行總結,包括以下內容 複製建構函式和過載賦值操作符的定義 複製建構函式和過載賦值操作符的呼叫時機 複製建構函式和過載賦值操作符的實現要點 複製建構函式的一些細節。複製建構函式和過載賦值操作符的定義 我們都知道,在c 中建立乙個類,這個類中肯定會包...
C 複製建構函式和賦值運算子過載函式
宣告乙個空的類testsize,sizeof testsize 為1,為其宣告建構函式和析構函式,依舊為1 建構函式不能使用關鍵字virtual,析構函式可以 一旦類中存在虛函式,就會為該類生成虛函式表,並在每乙個例項中新增乙個指向虛函式表的指標,從而大小為乙個指標大小,32位機器上為4,64位機器...