显式移动构造函数?
建议对所有大多数可以使用一个参数调用的构造函数使用explicit
关键字,复制构造函数除外。
对于复制构造函数,它有一个用途(禁止通过函数调用、返回等进行隐式复制),但这不是通常想要的。
那么移动构造函数呢?是否有任何合理的用例可以使它们变得明确?这里有什么好的做法?
The explicit
keyword is recommended for all most constructors which can be called with one argument, except for copy constructors.
For copy constructors, it has a use (to forbid implicit copying via function call, return, etc), but it's not what's usually wanted.
What about move constructors? Is there any reasonable use case to make them explicit? What's the good practice here?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(5)
显式
移动构造函数可能会影响与标准算法等的兼容性。例如,std::swap
要求T
可移动构造。反过来,MoveConstructible 是根据表达式指定的,即T u = rv;
(其中rv
是T
类型的右值)。如果给定类型既没有非显式复制构造函数,也没有非显式移动构造函数,则
T u = rv;
无效,并且该类型不能与std 一起使用: :交换
。 (然而,在这个特定的实例中,可以专门化std::swap
来提供所需的功能,例如通过使用T u(rv);
)。更简单地说,
显式
移动或复制构造函数违背了预期,并且不能与通用代码一起使用。标准库的其他一些部分提出了 MoveConstructible 要求:
unique_ptr
bind
(所有已衰退的类型)所涉及的传递)thread
、async
、call_once
(全部以调用包装器的形式指定)sort
、stable_sort
、nth_element
、sort_heap
An
explicit
move constructors can affect compatibility with e.g. Standard algorithms. For instance,std::swap<T>
requires thatT
be MoveConstructible. In turn, MoveConstructible is specified in terms of an expression, namelyT u = rv;
(whererv
is an rvalue of typeT
).If there is neither a non-explicit copy constructor nor a non-explicit move constructor for a given type then
T u = rv;
is invalid and that type can't be used withstd::swap
. (In this particular instance however it is possible to specializestd::swap
to provide the desired functionality, e.g. by usingT u(rv);
).Put more simply, an
explicit
move or copy constructor defies expectations and can't be used as well with generic code.Some other parts of the Standard library that put a MoveConstructible requirement:
unique_ptr<T, D>
bind
(all the decayed types that are passed are concerned)thread
,async
,call_once
(all specified in terms of call wrappers)sort
,stable_sort
,nth_element
,sort_heap
您可能需要一个隐式移动构造函数来满足大多数用途。它们通常与复制构造函数属于同一类别。不建议对所有单参数构造函数使用显式构造函数,但建议大多数构造函数使用显式构造函数。移动构造函数不在该列表中。
You probably want an implicit move constructor for the majority of uses. They generally fall into the same categories as copy constructors. Explicit isn't recommended for all one-argument constructors, but it is recommended for most. Move constructors are not on that list.
建议对(单参数)转换构造函数使用
explicit
关键字,以避免在意外位置发生意外转换。从这个意义上来说,复制构造函数和移动构造函数并不“令人惊讶”。它们大多发生在预期的地方。如果您不想要它们,我希望它们被标记为
=delete
而不是明确显示。The
explicit
keyword is recommended for (single argument) converting constructors, to avoid surprising conversions in unexpected places.Copy constructors and move constructors are hardly "surprising" in that sense. They happen largely where expected. If you don't want them, I would expect them to be marked
=delete
rather than made explicit.实际的问题是如何使用显式移动构造函数?它无法在右值上调用,因此编译器必须始终选择复制构造函数(如果可用),否则无法编译。
编辑:这里是示例的链接: http://www.ideone.com/nm7KM
The actual question is how explicit move constructor could possibly be used? It wouldn't be able to be invoked on rvalues, so compiler would have to always select a copy constructor, if available, or fail to compile.
Edit: here is the link to example: http://www.ideone.com/nm7KM
当从函数按值返回时,隐式移动构造函数通常可以使过程更加高效。
When returning by value from a function, an implicit move constructor can usually make the process more efficient.