简体   繁体   English

在什么情况下,从std :: forward进行分配比从std :: move进行分配优先? 为什么?

[英]What are the scenarios where assignment from std::forward is preferable over assignment from std::move ? why?

While learning about std::exchange on cppreference.com , I came across its "possible implementation" which is pasted below. cppreference.com上了解std::exchange时,我遇到了粘贴在下面的“可能的实现”。

  template<class T, class U = T>
  T exchange(T& obj, U&& new_value)
  {
      T old_value = std::move(obj);
      obj = std::forward<U>(new_value);
      return old_value;
  }

It looked a bit odd to see obj = std::forward in an assignment statement instead instead of std::move , which I think would have the same effect. 在赋值语句中看到obj = std::forward而不是std::move看起来有点奇怪,我认为这会产生相同的效果。

My understanding is that std::move is equivalent to a static_cast to rvalue reference type (but more expressive) and returns an xvalue always, whereas std::forward returns the same value type it is passed. 我的理解是std::move等效于static_cast到rvalue引用类型(但更具表达性),并且始终返回xvalue,而std::forward返回所传递的相同值类型。

My question is why is std:forward used in above snippet? 我的问题是为什么在上述代码段中使用std:forward and is there an easy rule of thumb to decide when this is the better choice? 是否有一个简单的经验法则来决定何时才是更好的选择?

The fact that there's assignment is irrelevant. 有分配的事实是无关紧要的。 What distinguishes forward from move is what kind of argument they take when used inside your function: 从什么区别此举是向前自己的函数中使用时,他们采取什么样的说法

  • The argument of forward is a forwarding reference parameter of your function. forward参数是函数的转发参考参数。
  • The argument of move is an rvalue reference parameter of your function (or more generally, anything you know to have no further aliases). move的参数是函数的右值引用参数(或更一般而言,您知道没有其他别名的任何东西)。

If you exchange with an lvalue, you don't want that to be moved-from! 如果与左值exchange ,则不希望将其移出!

For example, consider: 例如,考虑:

std::vector<int> a, b;

f(std::exchange(a, b));

This effectively calls f(a) but also performs a = b; 这有效地调用f(a)但也执行a = b; . It does not perform a = std::move(b) ; 执行a = std::move(b) ; b is still usable in its original form afterwards! b仍可按其原始形式使用!

See also this answer of mine, as well as many other related answers like What is std::move(), and when should it be used? 另请参阅我的答案以及其他许多相关答案,例如std :: move()是什么,何时使用它? , What's the difference between std::move and std::forward , and links therein. std :: move和std :: forward和其中的链接有什么区别

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

相关问题 std ::移动和地图分配 - std::move and map assignment 从内部替换std :: function(通过move-assignment到* this?) - Replacing std::function from within itself (by move-assignment to *this?) 我应该在移动ctors /赋值运算符中使用std :: move或std :: forward吗? - Should I use std::move or std::forward in move ctors/assignment operators? 在标准移动中没有复制的分配 - Assignment without copy in std move 从 std::exception 派生的 class 的赋值运算符 - assignment operator for class derived from std::exception 移动分配时左侧 std::vector 资源会发生什么变化? - What happens to the left hand side std::vector resources on move assignment? std :: move里面的移动赋值运算符 - std::move inside move assignment operator std :: move_if_noexcept调用copy-assignment,即使move-assignment是noexcept; 为什么? - std::move_if_noexcept calls copy-assignment even though move-assignment is noexcept; why? GCC C++11 删除移动可分配类的复制分配会阻止 std::sort 编译? - GCC C++11 deleting copy assignment for move assignable classes prevents std::sort from compiling? 为什么在移动赋值运算符中对内置类型使用 std::swap 而不是赋值? - Why use std::swap instead of assignment for built-in types in a move assignment operator?
 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM