Reputation: 5
I am confused about how copying objects works. If I make a copy of an object, what would happen if the copied object is deleted? Why? In my case, I thought the b1.test
would be undefined since the original object was deleted.
class blog
{
public:
int test;
blog() = default;
blog(int input) :test(input) {}
};
int main()
{
blog b1;
{
blog b2 = 1;
b1 = b2;
std::cout << b1.test << std::endl;
}
std::cout << b1.test << std::endl;
}
Upvotes: 0
Views: 124
Reputation: 1996
A copy is a new object. It has its own memory and its own lifecycle. Same with moves as well. Suppose you have the following struct:
struct my_object
{
std::string m_name;
my_object(const std::string &name) :
m_name{name}
{
std::cout << m_name << " constructed: " << this << '\n';
}
my_object(const my_object &o) :
m_name{"copied " + o.m_name}
{
std::cout << m_name << " constructed: " << this << '\n';
}
my_object(my_object &&o) :
m_name{"moved " + o.m_name}
{
std::cout << m_name << " constructed: " << this << '\n';
}
~my_object()
{
std::cout << m_name << " destructed: " << this << '\n';
}
};
If you do the following:
auto
main() -> int
{
my_object o1{"o1"};
my_object o2{"o2"};
{
auto o3 = o1;
auto o4 = std::move(o2);
}
return 0;
}
You get:
o1 constructed: 0x7ffe72e0f450
o2 constructed: 0x7ffe72e0f430
copied o1 constructed: 0x7ffe72e0f3f0
moved o2 constructed: 0x7ffe72e0f410
moved o2 destructed: 0x7ffe72e0f410
copied o1 destructed: 0x7ffe72e0f3f0
o2 destructed: 0x7ffe72e0f430
o1 destructed: 0x7ffe72e0f450
As shown above, we have 4 different memory addresses as we have created 4 different objects, each with their own lifecycles.
Upvotes: 2
Reputation: 11291
In main(), when you create object b1, it is put on the stack. Then within the scope you create, you make a new object b2, which it's also put on the stack /after/ b1. You then use an implicit assignment operator, which copies the internal value from object b2 to the internal value of object b1. At the end of the scope b2 is removed, but b1 still exists. Thus the internal value will still be what you copied from b2.
So you are not having two objects that reference the same memory space, but we're talking about two separate entities.
Upvotes: 1
Reputation: 238461
Let's say you have a piece of paper.
Now, take another paper that has some number on it.
Copy the number onto your first piece of paper.
Burn the paper that you copied from.
Did something happen to the paper that you copied to? No; it is independent from the other paper. This is how objects behave in C++. (References are different from objects, but you don't have any in the example).
Upvotes: 1
Reputation: 9078
Quentin gave you the simple answer. A copy is a copy. Imagine if you do this:
int a;
{
int b = 3;
a = b;
}
cout << a << endl;
You'll get 3 even though b is gone. This is because a is a copy of b.
In your code, you're doing the same thing, it's just that you're copying an entire object, not just a simple integer.
Just remember that copying objects can be expensive if it's a complicated object.
Note, however, that this is VERY different if you were keeping pointers, like this:
int * a = nullptr;
{
int b = 3;
a = &b;
}
cout << "A: " *a << endl;
At this point, you'll probably get expected results because this is such a simple problem, but it's really quite naughty as a points to some random location of memory that is no longer associated with something. If there were intervening code before the cout, you would almost certainly not get what you might want.
So be careful with pointers to objects that get destroyed.
Upvotes: 1