Kol*_*nya 10 c++ constructor move-constructor c++11 c++14
尝试编译以下代码:
struct Foo
{
explicit Foo ( void ) { }
explicit Foo ( Foo&& rhs ) { }
};
Foo bar ( void )
{
return Foo();
}
Run Code Online (Sandbox Code Playgroud)
收到以下错误:
调用隐式删除的'Foo'复制构造函数
好吧,很明显,拷贝代码被隐式删除了.
问题1:为什么编译器需要copy-ctor Foo?我期望使用move-ctor bar从rvalue构造返回值Foo().
然后我将move-ctor重新声明为隐式,并且所有内容都成功编译.
问题2:当我将move-ctor重新声明为隐式时,为什么编译器不再需要copy-ctor?
问题3:什么是explicit关键词意味着副本的背景和移动构建函数,因为它肯定意味着什么从正规构建函数的背景不同.
Mar*_*cia 10
这是因为返回值被认为是隐式转换.
引用C++ 11标准:
6.6.3退货声明
2 [...]
表达式为非void类型的return语句只能用于返回值的函数; 表达式的值返回给函数的调用者.表达式的值隐式转换为它出现的函数的返回类型.返回语句可能涉及构造和复制或移动临时对象(12.2).[...]
从返回表达式到临时对象的转换以保存返回值是隐式的.因此,这会导致错误
Foo f = Foo(); // Copy initialization, which means implicit conversion
Run Code Online (Sandbox Code Playgroud)
以代码为例也可以触发类似代码.
问题1:为什么编译器需要Foo的copy-ctor?我期望使用move-ctor从rvalue Foo()构造bar的返回值.
Foo(Foo&&)由于上述原因,这是因为不是可行的超载.规则规定,无论何时移动构造函数都不能使用,编译器应该考虑复制构造函数,在您的情况下,由于存在用户定义的移动构造函数,它会被隐式删除.
问题2:当我将move-ctor重新声明为隐式时,为什么编译器不再需要copy-ctor?
这是因为你的移动构造函数现在可以使用了.因此,编译器可以立即使用它,甚至不考虑复制构造函数的存在.
问题3:显式关键字在复制和移动ctors的上下文中意味着什么,因为它肯定意味着与常规ctors的上下文不同.
恕我直言,它没有意义,它只会导致问题,就像你的情况一样.
返回类型bar是Foo.没有复制构造函数,并且显式移动构造函数无法工作,因为仍然需要在和之间进行隐式转换.从这个意义上说,与任何其他转换构造函数没有什么不同.从不同类型的转换仍然会出现问题.这是一个类似的例子:Foo&&Fooexplicit Foo(Foo&&)explicitint
struct Foo
{
explicit Foo(int) {}
};
Foo bar ( void )
{
return 42; // error: could not convert '42' from 'int' to 'Foo'
}
Run Code Online (Sandbox Code Playgroud)
Q1:因为没有别的东西可以使用.
Q2:因为它使用移动构造函数来隐式转换Foo&&为Foo.
Q3:它与普通转换构造函数的含义相同.
| 归档时间: |
|
| 查看次数: |
1156 次 |
| 最近记录: |