logo

C++ Конструктор за копиране

Конструкторът за копиране е претоварени конструктор, използван за деклариране и инициализиране на обект от друг обект.

Конструкторът за копиране е два вида:

    Конструктор за копиране по подразбиране:Компилаторът дефинира конструктора за копиране по подразбиране. Ако потребителят не дефинира конструктор за копиране, компилаторът предоставя своя конструктор.Дефиниран от потребителя конструктор:Програмистът дефинира дефинирания от потребителя конструктор.
C++ Конструктор за копиране

Синтаксис на дефиниран от потребителя конструктор за копиране:

 Class_name(const class_name &old_object); 

Помислете за следната ситуация:

опа
 class A { A(A &x) // copy constructor. { // copyconstructor. } } 

В горния случай, Конструкторът за копиране може да бъде извикан по следните начини:

C++ Конструктор за копиране

Нека видим прост пример за конструктора за копиране.

// програма на конструктора за копиране.

 #include using namespace std; class A { public: int x; A(int a) // parameterized constructor. { x=a; } A(A &amp;i) // copy constructor { x = i.x; } }; int main() { A a1(20); // Calling the parameterized constructor. A a2(a1); // Calling the copy constructor. cout&lt; <a2.x; return 0; } < pre> <p> <strong>Output:</strong> </p> <pre> 20 </pre> <h2>When Copy Constructor is called</h2> <p>Copy Constructor is called in the following scenarios:</p> <ul> <li>When we initialize the object with another existing object of the same class type. For example, Student s1 = s2, where Student is the class.</li> <li>When the object of the same class type is passed by value as an argument.</li> <li>When the function returns the object of the same class type by value.</li> </ul> <h2>Two types of copies are produced by the constructor:</h2> <ul> <li>Shallow copy</li> <li>Deep copy</li> </ul> <h2>Shallow Copy</h2> <ul> <li>The default copy constructor can only produce the shallow copy.</li> <li>A Shallow copy is defined as the process of creating the copy of an object by copying data of all the member variables as it is.</li> </ul> <p>Let&apos;s understand this through a simple example:</p> <pre> #include using namespace std; class Demo { int a; int b; int *p; public: Demo() { p=new int; } void setdata(int x,int y,int z) { a=x; b=y; *p=z; } void showdata() { std::cout &lt;&lt; &apos;value of a is : &apos; &lt; <a<< std::endl; std::cout << 'value of b is : ' < <b<< *p <<*p<< } }; int main() { demo d1; d1.setdata(4,5,7); d2="d1;" d2.showdata(); return 0; pre> <p> <strong>Output:</strong> </p> <pre> value of a is : 4 value of b is : 5 value of *p is : 7 </pre> <img src="//techcodeview.com/img/c-tutorial/75/c-copy-constructor-3.webp" alt="C++ Copy Constructor"> <p>In the above case, a programmer has not defined any constructor, therefore, the statement <strong>Demo d2 = d1;</strong> calls the default constructor defined by the compiler. The default constructor creates the exact copy or shallow copy of the existing object. Thus, the pointer p of both the objects point to the same memory location. Therefore, when the memory of a field is freed, the memory of another field is also automatically freed as both the fields point to the same memory location. This problem is solved by the <strong>user-defined constructor</strong> that creates the <strong>Deep copy</strong> .</p> <h2>Deep copy</h2> <p>Deep copy dynamically allocates the memory for the copy and then copies the actual value, both the source and copy have distinct memory locations. In this way, both the source and copy are distinct and will not share the same memory location. Deep copy requires us to write the user-defined constructor.</p> <p>Let&apos;s understand this through a simple example.</p> <pre> #include using namespace std; class Demo { public: int a; int b; int *p; Demo() { p=new int; } Demo(Demo &amp;d) { a = d.a; b = d.b; p = new int; *p = *(d.p); } void setdata(int x,int y,int z) { a=x; b=y; *p=z; } void showdata() { std::cout &lt;&lt; &apos;value of a is : &apos; &lt; <a<< std::endl; std::cout << 'value of b is : ' < <b<< *p <<*p<< } }; int main() { demo d1; d1.setdata(4,5,7); d2="d1;" d2.showdata(); return 0; pre> <p> <strong>Output:</strong> </p> <pre> value of a is : 4 value of b is : 5 value of *p is : 7 </pre> <img src="//techcodeview.com/img/c-tutorial/75/c-copy-constructor-4.webp" alt="C++ Copy Constructor"> <p>In the above case, a programmer has defined its own constructor, therefore the statement <strong>Demo d2 = d1;</strong> calls the copy constructor defined by the user. It creates the exact copy of the value types data and the object pointed by the pointer p. Deep copy does not create the copy of a reference type variable.</p> <h2>Differences b/w Copy constructor and Assignment operator(=)</h2> <table class="table"> <tr> <th>Copy Constructor</th> <th>Assignment Operator</th> </tr> <tr> <td>It is an overloaded constructor.</td> <td>It is a bitwise operator.</td> </tr> <tr> <td>It initializes the new object with the existing object.</td> <td>It assigns the value of one object to another object.</td> </tr> <tr> <td>Syntax of copy constructor: <br> Class_name(const class_name &amp;object_name) <br> { <br> // body of the constructor. <br> }</td> <td>Syntax of Assignment operator: <br> Class_name a,b; <br> b = a;</td> </tr> <tr> <td><ul> <li>The <strong>copy constructor</strong> is invoked when the new object is initialized with the existing object.</li> <li>The object is passed as an argument to the function.</li> <li>It returns the object.</li> </ul></td> <td>The <strong>assignment operator</strong> is invoked when we assign the existing object to a new object.</td> </tr> <tr> <td>Both the existing object and new object shares the different memory locations.</td> <td>Both the existing object and new object shares the same memory location.</td> </tr> <tr> <td>If a programmer does not define the copy constructor, the compiler will automatically generate the implicit default copy constructor. </td> <td>If we do not overload the &apos;=&apos; operator, the bitwise copy will occur.</td> </tr> </table> <hr></a<<></pre></a<<></pre></a2.x;>

Когато се извика Copy Constructor

Конструкторът за копиране се извиква в следните сценарии:

  • Когато инициализираме обекта с друг съществуващ обект от същия тип клас. Например Student s1 = s2, където Student е класът.
  • Когато обектът от същия тип клас се предава по стойност като аргумент.
  • Когато функцията връща обект от същия тип клас по стойност.

Два вида копия се произвеждат от конструктора:

  • Плитко копие
  • Дълбоко копие

Плитко копие

  • Конструкторът за копиране по подразбиране може да създаде само плитко копие.
  • Плиткото копие се дефинира като процес на създаване на копие на обект чрез копиране на данни от всички членски променливи такива, каквито са.

Нека разберем това чрез прост пример:

 #include using namespace std; class Demo { int a; int b; int *p; public: Demo() { p=new int; } void setdata(int x,int y,int z) { a=x; b=y; *p=z; } void showdata() { std::cout &lt;&lt; &apos;value of a is : &apos; &lt; <a<< std::endl; std::cout << \'value of b is : \' < <b<< *p <<*p<< } }; int main() { demo d1; d1.setdata(4,5,7); d2="d1;" d2.showdata(); return 0; pre> <p> <strong>Output:</strong> </p> <pre> value of a is : 4 value of b is : 5 value of *p is : 7 </pre> <img src="//techcodeview.com/img/c-tutorial/75/c-copy-constructor-3.webp" alt="C++ Copy Constructor"> <p>In the above case, a programmer has not defined any constructor, therefore, the statement <strong>Demo d2 = d1;</strong> calls the default constructor defined by the compiler. The default constructor creates the exact copy or shallow copy of the existing object. Thus, the pointer p of both the objects point to the same memory location. Therefore, when the memory of a field is freed, the memory of another field is also automatically freed as both the fields point to the same memory location. This problem is solved by the <strong>user-defined constructor</strong> that creates the <strong>Deep copy</strong> .</p> <h2>Deep copy</h2> <p>Deep copy dynamically allocates the memory for the copy and then copies the actual value, both the source and copy have distinct memory locations. In this way, both the source and copy are distinct and will not share the same memory location. Deep copy requires us to write the user-defined constructor.</p> <p>Let&apos;s understand this through a simple example.</p> <pre> #include using namespace std; class Demo { public: int a; int b; int *p; Demo() { p=new int; } Demo(Demo &amp;d) { a = d.a; b = d.b; p = new int; *p = *(d.p); } void setdata(int x,int y,int z) { a=x; b=y; *p=z; } void showdata() { std::cout &lt;&lt; &apos;value of a is : &apos; &lt; <a<< std::endl; std::cout << \'value of b is : \' < <b<< *p <<*p<< } }; int main() { demo d1; d1.setdata(4,5,7); d2="d1;" d2.showdata(); return 0; pre> <p> <strong>Output:</strong> </p> <pre> value of a is : 4 value of b is : 5 value of *p is : 7 </pre> <img src="//techcodeview.com/img/c-tutorial/75/c-copy-constructor-4.webp" alt="C++ Copy Constructor"> <p>In the above case, a programmer has defined its own constructor, therefore the statement <strong>Demo d2 = d1;</strong> calls the copy constructor defined by the user. It creates the exact copy of the value types data and the object pointed by the pointer p. Deep copy does not create the copy of a reference type variable.</p> <h2>Differences b/w Copy constructor and Assignment operator(=)</h2> <table class="table"> <tr> <th>Copy Constructor</th> <th>Assignment Operator</th> </tr> <tr> <td>It is an overloaded constructor.</td> <td>It is a bitwise operator.</td> </tr> <tr> <td>It initializes the new object with the existing object.</td> <td>It assigns the value of one object to another object.</td> </tr> <tr> <td>Syntax of copy constructor: <br> Class_name(const class_name &amp;object_name) <br> { <br> // body of the constructor. <br> }</td> <td>Syntax of Assignment operator: <br> Class_name a,b; <br> b = a;</td> </tr> <tr> <td><ul> <li>The <strong>copy constructor</strong> is invoked when the new object is initialized with the existing object.</li> <li>The object is passed as an argument to the function.</li> <li>It returns the object.</li> </ul></td> <td>The <strong>assignment operator</strong> is invoked when we assign the existing object to a new object.</td> </tr> <tr> <td>Both the existing object and new object shares the different memory locations.</td> <td>Both the existing object and new object shares the same memory location.</td> </tr> <tr> <td>If a programmer does not define the copy constructor, the compiler will automatically generate the implicit default copy constructor. </td> <td>If we do not overload the &apos;=&apos; operator, the bitwise copy will occur.</td> </tr> </table> <hr></a<<></pre></a<<>
C++ Конструктор за копиране

В горния случай програмистът не е дефинирал никакъв конструктор, следователно операторът Демонстрация d2 = d1; извиква конструктора по подразбиране, дефиниран от компилатора. Конструкторът по подразбиране създава точно копие или плитко копие на съществуващия обект. По този начин указателят p и на двата обекта сочи към едно и също място в паметта. Следователно, когато паметта на едно поле се освободи, паметта на друго поле също се освобождава автоматично, тъй като и двете полета сочат към едно и също място в паметта. Този проблем се решава от дефиниран от потребителя конструктор което създава Дълбоко копие .

javascript коментар

Дълбоко копие

Дълбокото копиране динамично разпределя паметта за копието и след това копира действителната стойност, като източникът и копието имат различни места в паметта. По този начин както източникът, така и копието са различни и няма да споделят едно и също място в паметта. Дълбокото копиране изисква да напишем дефинирания от потребителя конструктор.

Нека разберем това чрез прост пример.

 #include using namespace std; class Demo { public: int a; int b; int *p; Demo() { p=new int; } Demo(Demo &amp;d) { a = d.a; b = d.b; p = new int; *p = *(d.p); } void setdata(int x,int y,int z) { a=x; b=y; *p=z; } void showdata() { std::cout &lt;&lt; &apos;value of a is : &apos; &lt; <a<< std::endl; std::cout << \'value of b is : \' < <b<< *p <<*p<< } }; int main() { demo d1; d1.setdata(4,5,7); d2="d1;" d2.showdata(); return 0; pre> <p> <strong>Output:</strong> </p> <pre> value of a is : 4 value of b is : 5 value of *p is : 7 </pre> <img src="//techcodeview.com/img/c-tutorial/75/c-copy-constructor-4.webp" alt="C++ Copy Constructor"> <p>In the above case, a programmer has defined its own constructor, therefore the statement <strong>Demo d2 = d1;</strong> calls the copy constructor defined by the user. It creates the exact copy of the value types data and the object pointed by the pointer p. Deep copy does not create the copy of a reference type variable.</p> <h2>Differences b/w Copy constructor and Assignment operator(=)</h2> <table class="table"> <tr> <th>Copy Constructor</th> <th>Assignment Operator</th> </tr> <tr> <td>It is an overloaded constructor.</td> <td>It is a bitwise operator.</td> </tr> <tr> <td>It initializes the new object with the existing object.</td> <td>It assigns the value of one object to another object.</td> </tr> <tr> <td>Syntax of copy constructor: <br> Class_name(const class_name &amp;object_name) <br> { <br> // body of the constructor. <br> }</td> <td>Syntax of Assignment operator: <br> Class_name a,b; <br> b = a;</td> </tr> <tr> <td><ul> <li>The <strong>copy constructor</strong> is invoked when the new object is initialized with the existing object.</li> <li>The object is passed as an argument to the function.</li> <li>It returns the object.</li> </ul></td> <td>The <strong>assignment operator</strong> is invoked when we assign the existing object to a new object.</td> </tr> <tr> <td>Both the existing object and new object shares the different memory locations.</td> <td>Both the existing object and new object shares the same memory location.</td> </tr> <tr> <td>If a programmer does not define the copy constructor, the compiler will automatically generate the implicit default copy constructor. </td> <td>If we do not overload the &apos;=&apos; operator, the bitwise copy will occur.</td> </tr> </table> <hr></a<<>
C++ Конструктор за копиране

В горния случай програмистът е дефинирал свой собствен конструктор, следователно оператора Демонстрация d2 = d1; извиква конструктора за копиране, дефиниран от потребителя. Той създава точното копие на стойностните типове данни и обекта, посочен от показалеца p. Дълбокото копиране не създава копие на променлива от референтен тип.

Разлики b/w Конструктор за копиране и оператор за присвояване (=)

Конструктор за копиране Оператор за присвояване
Това е претоварен конструктор. Това е побитов оператор.
Той инициализира новия обект със съществуващия обект. Той присвоява стойността на един обект на друг обект.
Синтаксис на конструктора за копиране:
Име_на_клас (const име_на_клас &име_на_обект)
{
// тялото на конструктора.
}
Синтаксис на оператора за присвояване:
Име_на_клас a,b;
b = a;
  • The конструктор за копиране се извиква, когато новият обект се инициализира със съществуващия обект.
  • Обектът се предава като аргумент на функцията.
  • Връща обекта.
The оператор за присвояване се извиква, когато присвоим съществуващия обект на нов обект.
Както съществуващият обект, така и новият обект споделят различни места в паметта. Както съществуващият обект, така и новият обект споделят едно и също място в паметта.
Ако програмистът не дефинира конструктора за копиране, компилаторът автоматично ще генерира неявния конструктор за копиране по подразбиране. Ако не претоварим оператора „=“, ще се получи побитово копиране.