C++ 为什么在删除“移动构造函数”时使用“复制构造函数”?
作为主题,相关代码为:C++ 为什么在删除“移动构造函数”时使用“复制构造函数”?,c++,c++11,constructor,copy-constructor,move-semantics,C++,C++11,Constructor,Copy Constructor,Move Semantics,作为主题,相关代码为: #include <iostream> class ABC { public: ABC() { std::cout<< "default construction" << std::endl; } ABC(const ABC& a) { std::cout << "copy construction" <&
#include <iostream>
class ABC
{ public:
ABC()
{
std::cout<< "default construction" << std::endl;
}
ABC(const ABC& a)
{
std::cout << "copy construction" << std::endl;
}
ABC(const ABC&& a)
{
std::cout << "move construction" << std::endl;
}
};
int main()
{
ABC c1 = ABC();
return 0;
}
如果删除上面的移动构造函数,则输出为:
default construction
copy construction
为什么在删除移动构造函数
时可以使用复制构造函数
呢?您可以看到,如果有用户定义的移动构造函数
,编译器更喜欢使用移动构造函数
根据一些文档,编译器提供了一个默认的移动构造函数
**,那么为什么编译器不使用默认的移动构造函数
?
我是C++初学者,很感谢能对这个问题有所帮助。
根据一些文档,编译器提供了一个默认的move构造函数
让我们看一些文档。以下内容来自
如果[conditions],则编译器将使用签名T::T(T&&)
将移动构造函数声明为其类的非显式内联公共成员
你说得对。编译器确实在正确的条件下提供了一个defualt move构造函数。然而,这些条件很重要。您似乎知道的第一个条件是:不能有用户定义的移动构造函数。因此,只剩下以下条件列表:
- 没有用户声明的副本构造函数李>
- 没有用户声明的副本分配运算符李>
- 没有用户声明的移动分配运算符李>
- 没有用户声明的析构函数李>
就这样。用户定义的复制构造函数阻止编译器提供默认的移动构造函数。因此没有可使用的移动构造函数。感谢您的澄清。那么为什么在删除了
移动构造函数时可以使用复制构造函数
?您可以看到,如果有用户定义的移动构造函数
,编译器更喜欢使用移动构造函数
。如果移动构造函数
不可用,则通过正常函数匹配选择复制构造函数
。const ABC&
可以绑定到使用ABC()
创建的临时文件。在存在move-ctor
的情况下,ABC&
更匹配,因为不需要const转换@sunshilong369@User10482谢谢你的解释。是(C++的ABC和可以绑定到临时创建的ABC())由C++标准开发的吗?还有一个问题,为什么编译器抱怨“<代码> abc(CONSTABC)<代码>被ABC(ABC)?@孙世龙369右替换,编译器更喜欢使用移动构造函数而不是复制构造函数。然而,它更倾向于使用存在的东西,而不是不存在的东西。复制构造函数确实适合此用途,只是不如移动构造函数好。@sunshilong369您的构造从一个临时的ABC
对象开始,然后将该对象传输(移动或复制)到另一个对象。也就是说,move或copy构造函数的参数是临时对象。因此,询问ABC(ABC&)
就接近于询问ABC(const ABC&)
并不是一个动作。删除常量:ABC(ABC&&)
@谢谢。你能更详细地解释一下吗?我有点困惑,因为这个代码(删除关键字const
)[确实可以编译。似乎我错了。Cppreference说T(const T&)
不算作移动向量。无论如何。从阅读开始,然后按照专用向量/作业页的链接进行操作。@besc你认为T(T&&)
(无关键字const
)算作移动向量吗?
default construction
copy construction