move constructor and copy constructor in C++

吃可爱长大的小学妹 提交于 2019-12-01 09:27:55
tNode foo()
{
    tNode node;
    return node;
}

and

tNode n1 = foo();

Is responsible for the output of

a: 10,  tNode() is called at testCopyControl.cpp:13
a: 10,  move constructor tNode() is called at testCopyControl.cpp:31
a: 10, destructor ~tNode() is called at testCopyControl.cpp:40
a: 10,  move constructor tNode() is called at testCopyControl.cpp:31
a: 10, destructor ~tNode() is called at testCopyControl.cpp:40

And what you see is the default constructor being called and then node begin treated as an rvalue in the return statement to move it into the return value and then another move from the return value into n1

With

tNode foo2()
{
    std::unique_ptr<tNode> up = std::make_unique<tNode>(20);
    return *up;
}

The behavior is different as you are not returning a function local object. *up gives you a tNode& so the return statement can't treat it as an rvalue. Since it is an lvalue you have to call the copy constructor to copy it into the return value. Then, like the first example, the move constructor is called to move the object from the return value into n2.

The following code does not implicitly move the constructed object:

tNode foo2()
{
    std::unique_ptr<tNode> up = std::make_unique<tNode>(20);
    return *up;
}

This is because, however obvious/intuitive it might seem to us, the compiler cannot prove that it is safe to move-from the object contained by up. It's forced to return by copy.

You could force it to return by R-value by explicitly casting the object as such:

tNode foo2()
{
    std::unique_ptr<tNode> up = std::make_unique<tNode>(20);
    return std::move(*up);
}
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!