我想为 std::vector 实现一个具有移动语义的一元算术运算符。目的是避免运算符内部分配应用于右值。
问题:以下操作无法编译:c = -(a + b)
这不能编译的原因是因为二元算术运算符 + I 为 std::vector 实现返回一个 const 左值(这样编译器会提示 (a + b) = c,这没有意义) .
二元 + 运算符
template<class T, class AllocVect1, class AllocVect2>
inline const std::vector<T> operator+ (
const std::vector<T, AllocVect1> &v1,
const std::vector<T, AllocVect2> &v2) {
std::vector<T> vout;
*Compute vout = v1 + v2*
return vout;
}
一元运算符
template<class T, class Alloc>
inline const std::vector<T>& operator- (std::vector<T, Alloc> &&v) {
std::transform (
v.begin (),
v.end (),
v.begin (),
[](const auto &val){return -val;});
return v;
}
按值传递和返回 vector 。
一旦你考虑这些事情,听起来可能不直观的东西是有道理的:
可以将临时对象隐式移动到值参数中——不会发生复制。这就像您要对局部变量调用 std::move
。
这个对象(参数)可以就地修改,因为它没有 const
限定符。
可以返回修改后的对象,并再次隐式应用移动语义。您永远不应返回对局部变量的引用——既不是左值引用也不是右值引用。
template<class T>
std::vector<T> operator-(std::vector<T> v) { // 1.
std::for_each( // 2.
v.begin(),
v.end(),
[](T& val) {val = -val;});
return v; // 3.
}
此运算符可以用右值(移动 + 修改 + 移动)和左值(复制 + 修改 + 移动)调用。
这就是说,有const Param&
和Param&&
的单独重载的优点,其细节已在单独的答案中解释:
我是一名优秀的程序员,十分优秀!