Home > Back-end >  why am I able to copy one object into other object if the class has a const variable?
why am I able to copy one object into other object if the class has a const variable?

Time:01-21

As per cppreference documentation :

The implicitly-declared or defaulted copy constructor for class T is defined as deleted if any of the following conditions are true:

  • T has non-static data members that cannot be copied (have deleted, inaccessible, or ambiguous copy constructors);

I am using a const variable inside my Demo class, so I am expecting that obj1 should not copy into obj2 because we have a const variable, as shown in the below example:

#include <iostream>
using namespace std;

class Demo
{
public:
  const int val = 100;//nonstatic data member that cannot be copied
  Demo(){}    
};

int main()
{
    Demo obj1;
    Demo obj2(obj1);
    std::cout << "obj1.val :" << obj1.val << std::endl;
    std::cout << "obj2.val :" << obj2.val << std::endl;
    return 0;
}

Output:

obj1.val : 100
obj2.val : 100

Why is obj1 copied into obj2? As per cppreference doc: "implicitly declared copy constructor deleted if you have nonstatic data member which cannot be copied"

CodePudding user response:

why obj1 copied into obj2? as per cppreference doc "implicitly declared copy constructor deleted

Because the implicitly declared copy ctor Demo::Demo(const Demo&) is not actually deleted in the given code as the const data member val can be copied.


so could you tell me any datamember example that we cannot copy just to understand this point?

Here is a contrived example where the copy ctor Demo::Demo(const Demo&) is implicitly deleted as the const data member val cannot be copied.

class DeletedCopy
{
    public:
        DeletedCopy(const DeletedCopy&) = delete;//delete the copy ctor
        DeletedCopy() = default;
};
class Demo
{
public:
  const DeletedCopy val{};
  Demo(){}

};

int main()
{
    Demo obj1;
    Demo obj2(obj1);//this won't work now as copy ctor Demo::Demo(const Demo&) is implicitly deleted.
    return 0;
}

Demo

CodePudding user response:

1. Your initial question:

Why is obj1 copied into obj2

Because having a const member does not mean it cannot be copied. const just means that once the member is initialized it cannot be modified.

2. Your question in the comment:

could you tell me any datamember example that we cannot copy just to understand this point?

You'll need to add a member which is non-copyable in order to have the "implicitly declared copy constructor deleted".
An example is std::mutex:

The following code produces the error message below:

#include <mutex>

class Demo
{
public:
    std::mutex val;
};

int main()
{
    Demo obj1;
    Demo obj2(obj1);  // <---- error below on this line
    return 0;
}

Error message (MSVC):

error C2280: 'Demo::Demo(const Demo &)': attempting to reference a deleted function

A side note: better to avoid using namespace std - see here Why is "using namespace std;" considered bad practice?.

  • Related