C 深拷貝與淺拷貝的區別

2021-07-11 02:52:33 字數 1411 閱讀 3796

**:

又加了一些自己補充。

原文:memberwise copy: 在初始化乙個物件期間,基類的建構函式被呼叫,成員變數被呼叫,如果它們有建構函式的時候,它們的建構函式被呼叫,這個過程是乙個遞迴的過程.

bitwise copy: 原記憶體拷貝.例子,給定乙個物件object,它的型別是class base.物件object占用10位元組的記憶體,位址從0x0到0x9.如果還有乙個物件objecttwo,型別也是class base.那麼執行objecttwo = object;如果使用bitwise拷貝語義,那麼將會拷貝從0x0到0x9的資料到objecttwo的記憶體位址,.也就是說bitwise是位元組到位元組的拷貝.

對於預設的拷貝建構函式不會使用深拷貝,它只是使用淺拷貝.這意味著類的所有的成員是一層深度的拷貝而已。如果你的類或結構體成員中只是包含基本的資料型別例如int, float, char,那麼memberwise copy與bitwise copy基本是相同的。但如果類中有指標存在,那麼你可能會遇到問題。

例如下面的例子:

class a

;如果你建立兩個這樣的類物件,class a  a, b;並且你給a賦值,

a.mi = 6;

a.d1 = 10.123;

a.pstring = new char[10];

astrcpy(a.pstring, "test");//這裡是淺拷貝

如果執行b = a;那麼會把物件a的每乙個成員的值賦值給b的每個成員。

b.m1 = a.m1;

b.d1 = a.d1;

b.pstring = a.pstring;//現在物件a和b的成員pstring都執向相同的記憶體,刪除任乙個記憶體都會析放另乙個物件的記憶體。

所以你需要深拷貝,它不是拷貝的記憶體位址而是拷貝記憶體位址的內容。乙個預設的拷貝建構函式經常執行淺拷貝,只有擁有

自己的拷貝函式才可以實現深拷貝。

補充:在bitwise copy sematics中,因為是按位拷貝的(記憶體複製),所以那些整數、陣列等都會拷貝,新得到的類和原來的類完全一樣。但是需要注意一點,如果有指標時,例如

class test;

test b=a;//a是test類的物件

這時候如果是bitwise copy,那麼a和b中的指標p就會指向同一記憶體,如果內存在建構函式中釋放,那麼另乙個類的指標將失效。

在一下4中情況,不要bitwise copy

1、當class內的成員變數是乙個類,這各類宣告了copy constructor(不是編譯器預設合成)時。

2、當class繼承自乙個base class時,而base class存在copy constructor時(不是編譯器預設合成)。

3、當class中宣告有virtual function時

4、當class繼承自乙個繼承串鏈,其中乙個或多個virtual base class時。

C 淺拷貝與深拷貝區別

也許會有人這樣解釋c 中淺拷貝與深拷貝區別 淺拷貝是對引用型別拷貝位址,對值型別直接進行拷貝。不能說它完全錯誤,但至少還不夠嚴謹。比如 string 型別咋說?其實,我們可以通過實踐來尋找答案。首先,定義以下型別 int string enum struct class int string 如下 ...

C 淺拷貝與深拷貝區別

也許會有人這樣解釋c 中淺拷貝與深拷貝區別 淺拷貝是對引用型別拷貝位址,對值型別直接進行拷貝。不能說它完全錯誤,但至少還不夠嚴謹。比如 string 型別咋說?其實,我們可以通過實踐來尋找答案。首先,定義以下型別 int string enum struct class int string 如下 ...

c 深拷貝與淺拷貝區別

深拷貝和淺拷貝最根本的區別在於是否真正獲取乙個物件的複製實體,而不是引用。假設b複製了a,修改a的時候,看b是否發生變化 如果b跟著也變了,說明是淺拷貝,拿人手短!修改堆記憶體中的同乙個值 如果b沒有改變,說明是深拷貝,自食其力!修改堆記憶體中的不同的值 淺拷貝 shallowcopy 只是增加了乙...