C ++移动构造函数未调用右值引用 [英] C++ move constructor not called for rvalue reference
问题描述
class MyClass {
public:
MyClass()
{
std::cout << "default constructor\n";
}
MyClass(MyClass& a)
{
std::cout << "copy constructor\n";
}
MyClass(MyClass&& b)
{
std::cout << "move constructor\n";
}
};
void test(MyClass&& temp)
{
MyClass a(MyClass{}); // calls MOVE constructor as expected
MyClass b(temp); // calls COPY constructor... not expected...?
}
int main()
{
test(MyClass{});
return 0;
}
对于上面的代码,我希望在test()中创建的两个对象都可以调用move构造函数,因为b是r值引用类型(MyClass&&).
For the above code, I expected both object creations in test() to call move constructor because b is a r-value reference type (MyClass&&).
但是,将b传递给MyClasss构造函数不会像预期的那样调用move构造函数,而是调用copy构造函数.
However, passing b to the MyClasss constructor does not call move constructor as expected, but calls copy constructor instead.
即使传递的参数的类型为MyClass&& ;,为什么第二种情况也调用复制构造函数(r值参考)???
Why does second case calls copy constructor even if the passed argument is of type MyClass&& (r-value reference)???
我正在使用gcc 5.2.1.要重现我的结果,必须将-fno-elide-constructors选项传递给gcc以禁用复制删除优化.
I am using gcc 5.2.1. To reproduce my results, you must pass -fno-elide-constructors option to gcc to disable copy elision optimization.
void test(MyClass&& temp)
{
if (std::is_rvalue_reference<decltype(temp)>::value)
std::cout << "temp is rvalue reference!!\n";
else
std::cout << "temp is NOT rvalue!!\n";
}
即使命名为temp,以上代码也会打印出"temp is rvalue reference".
Above code prints out "temp is rvalue reference" even if temp is named.
temp的类型是右值引用类型.
temp's type is rvalue reference type.
推荐答案
void test(MyClass&& temp)
{
MyClass a(MyClass{}); // calls MOVE constructor as expected
MyClass b(temp); // calls COPY constructor... not expected...?
}
这是因为temp
(因为它具有名称)是对rvalue
的lvalue
引用.要随时将其视为rvalue
,请调用std::move
That is because, temp
(since it has a name,) is an lvalue
reference to an rvalue
. To treat as an rvalue
at any point, call on std::move
void test(MyClass&& temp)
{
MyClass a(MyClass{}); // calls MOVE constructor as expected
MyClass b(std::move(temp)); // calls MOVE constructor... :-)
}
这篇关于C ++移动构造函数未调用右值引用的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!