Perfect forwarding
12345678 | #include <utility>
template<typename T, typename U>
std::pair<T, U> make_pair_wrapper(T&& t, U&& u)
{
return std::make_pair(std::forward<T>(t),
std::forward<U>(u));
} |
This pattern is licensed under the CC0 Public Domain Dedication.
Intent
Forward arguments of one function to another as though the wrapped function had been called directly.
Description
Perfect forwarding allows us to preserve an argument’s value
category (lvalue/rvalue) and const
/volatile
modifiers. Perfect
forwarding is performed in two steps: receive a forwarding
reference (also known as universal reference), then forward it
using std::forward
.
In our example, the arguments t
and u
on line 4 are forwarding
references because they are declared in the form X&&
where X
is a template parameter. We use std::forward
on lines 6–7 to forward
these arguments to std::make_pair
,
allowing them to be moved into the pair when the original argument
was an rvalue expression.
Perfect forwarding is often used with variadic templates
to wrap calls to functions with an arbitrary number of arguments.
For example, std::make_unique
and std::make_shared
both
use perfect forwarding to forward their arguments to the
constructor of the wrapped type.