std :: move的简写

Ori*_*ent 1 c++ operator-overloading rvalue-reference move-semantics perfect-forwarding

对于某些类来说S,重载一元operator +(或者可能operator *是非指针式类)如下所示是不好的做法?

struct S { S && operator + () & noexcept { return std::move(*this); } };
Run Code Online (Sandbox Code Playgroud)

它的目标是发明速记std::move.

S a;
S b = +a;
// instead of
S c = std::move(a);
Run Code Online (Sandbox Code Playgroud)

假设我有一个包含大量不同类的项目,它集中使用了移动语义.所有类都不模仿任何算术对应物.

Bar*_*rry 15

做这样的事情客观上是不好的做法.std::move()是标准提供的,易于理解的转换为右值(特别是xvalue)的方法.任何看到的人std::move(a)都知道它究竟是做什么 - 或者不理解移动语义(如果他们不这样做,std::move谷歌很容易了解).

看到+a没有任何意义而不必先查找它.更糟糕的是,unary +对许多类型的预期意义- 与移动语义无关!(例如,是a一个char得到晋升int?它是一个没有捕获的λ得到转化为函数指针?)所有的只是保存10个字符?更不用说你必须operator+为每种类型实现这一点,而你根本不需要实现std::move().这是一个非常糟糕的权衡.


Mar*_*k B 9

我会反对这一点,原因与我们#define BEGIN {在C++中没有相同的原因:未来的代码维护者(甚至可能是)将无法立即理解正在发生的事情.

请记住,您只需编写一次代码并多次阅读.std::move如此快速地输入,清楚它正在做什么,任何了解C++ 11的人都会确切地知道它意味着什么.


hls*_*lon 8

正如Scott Meyers在更有效的C++第7项中所述:

运算符重载的目的是使程序更易于阅读,编写理解

+a;键入的字符越少......就是这样.你需要看看它每次去理解它的意思,读它是根本不清楚(+ +a,++a,- +a?).

使用std::move,因为它很容易读,写和理解.