What is the purpose of std::forward()'s rvalue reference overload?

会有一股神秘感。 提交于 2019-12-01 15:04:05

The design rationale for forward is discussed in great detail in N2951.

This document lays out 6 use cases:

A. Should forward an lvalue as an lvalue. All implementations pass this test. But this is not the classic perfect forwarding pattern. The purpose of this test is to show that implementation 2 fails in its stated goal of preventing all use cases except perfect forwarding.

B. Should forward an rvalue as an rvalue. Like use case A, this is an identity transformation and this presents a motivating example where the identity transformation is needed.

C. Should not forward an rvalue as an lvalue. This use case demonstrates a dangerous situation of accidentally creating a dangling reference.

D. Should forward less cv-qualified expressions to more cv-qualified expressions. A motivating use case involving the addition of const during the forward.

E. Should forward expressions of derived type to an accessible, unambiguous base type. A motivating use case involving forwarding a derived type to a base type.

F. Should not forward arbitrary type conversions. This use case demonstrates how arbitrary conversions within a forward lead to dangling reference run time errors.

The second overload enables cases B and C.

The paper goes on to provide examples of each use case, which are too lengthy to be repeated here.

Update

I've just run the "solution" of just the first overload through these 6 use cases, and this exercise shows that the second overload also enables use case F: Should not forward arbitrary type conversions.

Here's a very common usage for the second overload: generic lambda.

[](auto&& x) {
    return f(std::forward<decltype(x)>(x));
}

without the second overload, the code will be using std::conditional_t<std::is_rvalue_reference_v<decltype(x)>, ...>.

(See Scott Meyer's C++14 Lambdas and Perfect Forwarding)

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!