为了账号安全,请及时绑定邮箱和手机立即绑定

C+11返回值优化还是移动?

C+11返回值优化还是移动?

C++ C
手掌心 2019-07-04 13:31:50
C+11返回值优化还是移动?我不明白什么时候该用std::move当我应该让编译器优化.。例如:using SerialBuffer = vector< unsigned char >;// let compiler optimize itSerialBuffer read( size_t size ) const{     SerialBuffer buffer( size );     read( begin( buffer ), end( buffer ) );     // Return Value Optimization     return buffer;}// explicit moveSerialBuffer read( size_t size ) const{     SerialBuffer buffer( size );     read( begin( buffer ), end( buffer ) );     return move( buffer );}我该用哪一种?
查看完整描述

3 回答

?
慕无忌1623718

TA贡献1744条经验 获得超4个赞

只使用第一种方法:

Foo f(){
  Foo result;
  mangle(result);
  return result;}

这将已经允许使用移动构造函数(如果可用的话)。实际上,局部变量可以绑定到return当允许复制省略时,精确地声明。

您的第二个版本积极禁止复制省略。第一个版本普遍更好。


查看完整回答
反对 回复 2019-07-04
?
慕森卡

TA贡献1806条经验 获得超8个赞

所有返回值都已经moved或者优化出,因此不需要显式地使用返回值移动。

编译器允许自动移动返回值(优化副本),甚至优化移动!

N 3337标准草案第12.8节(C+11):

当满足某些条件时,即使对象的复制/移动构造函数和/或析构函数有副作用,也允许实现省略类对象的复制/移动构造。在这种情况下,实现将省略的复制/移动操作的源和目标简单地视为引用同一个对象的两种不同方式,而该对象的销毁发生在如果不进行优化就会销毁这两个对象的后期。复制省略,允许在下列情况下(可合并以消除多份副本):

[...]

:

class Thing {public:Thing();
   ~Thing();
   Thing(const Thing&);};Thing f() {
   Thing t;
   return t;}Thing t2 = f();

在这里,可以将省略的条件组合起来,以消除对类的复制构造函数的两个调用。Thing*复制本地自动对象t到函数返回值的临时对象中。f()以及将该临时对象复制到对象中。t2..有效地,局部对象的构造t可以被视为直接初始化全局对象。t2,该物体的破坏将发生在程序出口。向Thing具有相同的效果,但它是从临时对象移动到t2那是被剥夺的。-终例 ]

如果符合或将满足复制操作的省略条件,除非源对象是函数参数,并且要复制的对象由lvalue指定,则首先执行重载解析,以选择副本的构造函数,就好像该对象是由rvalue指定的一样。如果重载解析失败,或者所选构造函数的第一个参数的类型不是对象类型的rvalue引用(可能是cv限定的),则再次执行重载解析,将对象视为lvalue。


查看完整回答
反对 回复 2019-07-04
?
万千封印

TA贡献1891条经验 获得超3个赞

很简单。

return buffer;

如果你这样做,那么NRVO要么会发生,要么就不会发生。如果它不发生,那么buffer将被移出。

return std::move( buffer );

如果你这么做,那么NVRO不会发生,而且buffer将被移出。

所以使用std::move在这里,还有很多损失。

这条规则有一个例外:

Buffer read(Buffer&& buffer) {
    //...
    return std::move( buffer );}

如果buffer是一个rvalue引用,那么您应该使用std::move..这是因为引用不符合NRVO的条件,所以没有std::move它将产生一个来自lvalue的副本。

这只是“永远”这条规则的一个实例。movervalue引用和forward“通用引用”,优先于“从不”的规则。move返回值“。


查看完整回答
反对 回复 2019-07-04
  • 3 回答
  • 0 关注
  • 697 浏览

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信