forward — std::forward
forward — std::forward
std::forward는 완전 전달(perfect forwarding)을 위해, 인수의 원래 값 종류(lvalue/rvalue)를 그대로 유지하면서 전달하는 함수예요. C++11에서 도입됐어요. <utility> 헤더에 있어요.
템플릿 인자를 다른 함수로 "있는 그대로" 포워딩할 때 사용해요.
출처: cppreference
본문
// <utility> 헤더, C++11
template< class T >
constexpr T&& forward( std::remove_reference_t<T>& t ) noexcept;
template< class T >
constexpr T&& forward( std::remove_reference_t<T>&& t ) noexcept;
사용 예 — 완전 전달 팩토리
#include <utility>
#include <memory>
// args를 그대로 T 생성자에 전달
template<typename T, typename... Args>
std::unique_ptr<T> make(Args&&... args) {
return std::make_unique<T>(std::forward<Args>(args)...);
}
인자에 std::forward를 걸면, lvalue로 들어온 인자는 lvalue로, rvalue로 들어온 인자는 rvalue로 그대로 전달돼요. 이렇게 해야 이동·복사가 올바르게 선택돼요.
forwarding reference
template<typename T>
void wrapper(T&& x) { // T&&는 forwarding reference
inner(std::forward<T>(x)); // 값 종류 유지 전달
}
int n = 5;
wrapper(n); // T=int& → lvalue 전달
wrapper(5); // T=int → rvalue 전달
forward vs move
std::move(x)— 항상 rvalue로.std::forward<T>(x)—T가 lvalue 참조면 lvalue, 아니면 rvalue. (조건부)
void g(int&);
void g(int&&);
template<typename T>
void f(T&& t) {
g(std::forward<T>(t)); // 호출부 값 종류에 맞는 g 선택
}
주의
std::forward는 반드시 같은 타입의 템플릿 인자를 명시해 사용해요 (forward<T>).- forwarding reference(
T&&) 매개변수에만 의미가 있어요.
std::forward는 제네릭 코드에서 인자의 값 종류를 잃지 않고 전달하는 완전 전달의 핵심 도구예요. 래퍼·팩토리·타입 안전한 포워딩에 필수적이에요.