In VS2010 std::forward is defined as such:
template<class _Ty> inline
_Ty&& forward(typename identity<_Ty>::type& _Arg)
{ // forward _Arg, given explicitly specified type parameter
return ((_Ty&&)_Arg);
}
identity appears to be used solely to disable template argument deduction. What’s the point of purposefully disabling it in this case?
If you pass an rvalue reference to an object of type
Xto a template function that takes typeT&&as its parameter, template argument deduction deducesTto beX. Therefore, the parameter has typeX&&. If the function argument is an lvalue or const lvalue, the compiler deduces its type to be an lvalue reference or const lvalue reference of that type.If
std::forwardused template argument deduction:Since
objects with names are lvaluesthe only timestd::forwardwould correctly cast toT&&would be when the input argument was an unnamed rvalue (like7orfunc()). In the case of perfect forwarding theargyou pass tostd::forwardis an lvalue because it has a name.std::forward‘s type would be deduced as an lvalue reference or const lvalue reference. Reference collapsing rules would cause theT&&instatic_cast<T&&>(arg)in std::forward to always resolve as an lvalue reference or const lvalue reference.Example: