Copy Constructor in C++

Copy Constructor in C++

The copy constructor in C++ is a type of constructor that is used to create a new object as a copy of an existing object. It is important to handle resource management with dynamic memory. It is of two types: default and user-defined. In this article, we will discuss what a copy constructor in C++ is, when it is called, its types, shallow and deep copy, implicit and explicit copy constructors, the difference between copy constructors and assignment operators, why the rule of three matters, advantages, and disadvantages of copy constructors in C++.

Table of Contents:

What is a Copy Constructor in C++?

What is a Copy Constructor in C++

A copy constructor in C++ is a special constructor that is used to create a new object as a copy of an existing object. This constructor is called when an object is initialized from another object of the same class.

Syntax:

ClassName(const ClassName& other);
  • ClassName is the name of the class.
  • const is the parameter that prevents unnecessary copying in the source object.
  • &other is a reference to the source object.
  • other is the source object.

Example:

Cpp

Output:

What is a Copy Constructor in C++ Example

The code shows how the copy constructor in a C++ program creates a new object b2 as a copy of b1, and then copies and prints the title of the book as output.

When is the Copy Constructor Called in C++?

Below are a few situations where a copy constructor can be called in C++:

  • When a new object is created from an existing object.
  • When an object is passed by value.
  • When a function returns an object by value.
  • When an object is caught in a catch block by value.
  • When a temporary object is created and assigned to a new object without using move semantics.
  • When an STL container performs a copy internally in the function.
  • When copy elision is not applied.

Types of Copy Constructor in C++

There are two types of copy constructors in C++ that are classified on the basis of the data types used.

  1. Default Copy Constructor
  2. User-Defined Copy Constructor

Let’s discuss both types in brief with examples in C++:

Default Copy Constructor in C++

The default copy constructor is a type of copy constructor that is automatically generated by the compiler if it is not defined. It performs a shallow copy, which means that it simply copies the values of each member from one object to another. Also, this shallow copying can cause double deletion and incorrect copying of resources. It can be used for simple data members such as integers, strings, etc.

Example:

Cpp

Output:

Default Copy Constructor in C++

The code shows that the compiler provides a default copy constructor because no copy constructor is defined, and then copies the title from b1 to b2.

User-Defined Copy Constructor in C++

A user-defined copy constructor is a type of copy constructor in which the user can write their own to copy an object. It allows more control over how an object is copied when the object contains dynamically allocated memory. By using a user-defined copy constructor, you can implement deep copying.

Example:

Cpp

Output:

User-Defined Copy Constructor in C++

The code shows how a user-defined copy constructor performs a deep copy of a dynamically allocated name so that both objects, p1 and p2, manage separate memory.

Constructor Copies

Constructor Copies

There are two ways in which the constructor copies in C++.

  1. Shallow Copy
  2. Deep Copy

Shallow Copy in C++

Shallow Copy in C++

A shallow copy is a type of copying in which the values of data members are copied from one object to another, which means that it copies to the same memory location.

Characteristics:

  • It is created by the default or compiler-generated copy constructor.
  • There is no new memory allocation for pointer members.
  • It leads to shared ownership of the same resource.
  • It can cause double deletion and undefined behavior.

Example:

Cpp

Output:

Shallow Copy in C++

The code shows how the shallow copy is done, where both b1 and b2 share the same memory for the str, which then leads to a double deletion and potential crash when the program ends.

Deep Copy in C++

Deep Copy in C++

A deep copy in C++ is used to create an independent copy of an object with any dynamically allocated memory, so that the object can manage its own memory safety easily.

Characteristics:

  • It requires a user-defined copy constructor.
  • It allocates new memory for pointer members.
  • It avoids shared memory issues such as double deletion.
  • It makes sure that both the original and copied objects are fully independent.

Example:

Cpp

Output:

Deep Copy in C++

The code shows how the deep copy is used, where the copy constructor allocates new memory and copies by making sure that b1 and b2 manage memory separately.

Get 100% Hike!

Master Most in Demand Skills Now!

Shallow Copy vs Deep Copy in C++

Feature Shallow Copy Deep Copy
Definition Copies only the values of data members, including pointers Copies values and also allocates separate memory for pointers
Memory Sharing Copy the pointer addresses, both objects point to the same memory Allocates new memory and copies the actual data
Constructor Used Compiler-generated (default copy constructor) User-defined copy constructor
Performance Faster (less memory allocation) Slower (extra memory operations)
Use Case Safe for simple objects without dynamic memory Required when an object has dynamic memory or resources
Risk Risk of double deletion, dangling pointers Safer memory handling

Implicit vs Explicit Copy Constructors in C++

Feature Implicit Copy Constructor (Compiler Generated) Explicit Copy Constructor (User-Defined)
Definition Automatically generated by the compiler Written manually by the programmer
When Provided When no copy constructor is explicitly defined When custom copy behavior is needed
Copy Type Shallow copy (member-wise copy) Can implement shallow or deep copy
Customization Not customizable Fully customizable
Resource Management Not suitable for classes managing resources Suitable for classes with dynamic memory, files, etc.
Example Use Case Simple structs or classes with primitive types Classes with pointers or complex data members

Difference Between Copy Constructor and Assignment Operator in C++

Feature Copy Constructor Assignment Operator
Purpose Initializes a new object as a copy of an existing one Assigns values from one existing object to another
When can it be called When a new object is created from an existing object When an already initialized object is assigned another
Function Signature ClassName(const ClassName& other) ClassName& operator=(const ClassName& other)
Called On Uninitialized object Already initialized object
Memory Handling Typically allocates new memory for a deep copy Releases old memory (if any) and copies new data
Default Provided By Compiler (unless user-defined) Compiler (unless user-defined)
Example Class a = b; a = b;

Why the Rule of Three in C++ Matters for Copy Constructor?

The rule of three is very important if a class manages a resource such as dynamic memory or file handles, and then any one of the following is defined:

  1. Destructor
  2. Copy Constructor
  3. Copy Assignment Operator

Then all three must be defined explicitly. And if it fails to do so, then it may result in resource mismanagement such as double deletion, memory leaks, and shallow copy issues.

Thus, if a copy constructor is defined to perform a copy, and an assignment operator or destructor is not defined, then the class may not copy resources, which can lead to resource leaks.

Advantages of Copy Constructor in C++

  • It helps to simplify the object duplication for simple classes.
  • It supports custom copy logic or deep copy, which is ideal for handling dynamic memory resources.
  • The copy constructor keeps the copy logic encapsulated in the class to avoid repetitive copying.
  • It can integrate with STL containers such as vector, map, etc.
  • It makes sure that the object initialization through copying is predictable and consistent.

Disadvantages of Copy Constructor in C++

  • The default constructor performs shallow copies, which can lead to issues such as double deletion, dangling pointers, and shared resource conflicts.
  • Deep copying can give performance overhead for large and complex objects.
  • The code complexity increases due to using the copy constructor when the code has a class with dynamic memory.
  • This constructor can also give recursion errors if the code is not written properly.
  • If a copy constructor is defined but the assignment operator or destructor is not defined, then it may lead to resource leaks and undefined behavior.

Conclusion

The copy constructor is important in C++ to make an exact copy of any existing object, especially when dealing with dynamic memory classes. It is of two types: default and user-defined, which use different constructors for copying, such as shallow and deep copy. Also, this constructor has advantages and disadvantages that can affect C++ programming. So, by understanding what a copy constructor is, its types, uses, advantages, and disadvantages, you can easily use the copy constructor in your C++ programming.

FAQs on Copy Constructor in C++

Q1. What happens if I don't define a copy constructor?

If you don’t define a copy constructor compiler provides a default shallow copy constructor, which can cause issues for classes with dynamic memory.

Q2. Can I overload the copy constructor?

No, copy constructors cannot be overloaded; they must take a reference to the same class type.

Q3. When is the copy constructor called?

It is called when an object is initialized from another object, passed, or returned by value.

Q4. What is the difference between a copy constructor and an assignment operator?

A copy constructor creates a new object, and the assignment operator copies data into an existing object.

Q5. Why must the copy constructor take a reference?

The copy constructor must take a reference, as passing by value would lead to a recursive call, causing a compilation error.

About the Author

Technical Research Analyst - Full Stack Development

Kislay is a Technical Research Analyst and Full Stack Developer with expertise in crafting Mobile applications from inception to deployment. Proficient in Android development, IOS development, HTML, CSS, JavaScript, React, Angular, MySQL, and MongoDB, he’s committed to enhancing user experiences through intuitive websites and advanced mobile applications.

Full Stack Developer Course Banner