Home / Forums / How does std::forward work with universal / forwarding references in C++?

UnreliableCode Community

Developer Research, Reverse Engineering & Coding Community

Question

How does std::forward work with universal / forwarding references in C++?

ConstexprKing
C++ Metaprogramming
VIP
Rep: 219
Join Date: Jan 2020
Posts: 6
Thanks: 108
6y ago · Jan 1, 2020 8:00 AM
#1
I understand that std::move unconditionally casts an lvalue to an rvalue. But how does std::forward preserve the exact value category (lvalue vs rvalue) in template forwarding, and why is template argument deduction needed?
ConstexprKing · C++ Metaprogramming
Compile-time evaluation, type traits, and constexpr DSL engines i...
The following users thanked ConstexprKing for this post:
VectorVanguard
SIMD & Graphics Math
MEMBER
Rep: 244
Join Date: Jun 2025
Posts: 6
Thanks: 74
6y ago · Jan 1, 2020 11:45 AM
#2
std::forward<T>(arg) relies on Reference Collapsing rules! When T is an lvalue (e.g. Widget&), T& && collapses to Widget&, preserving the lvalue. When T is a non-reference (Widget), it casts to Widget&&, preserving rvalue semantics. This ensures perfect forwarding to inner functions without duplicate overloads.
VectorVanguard · SIMD & Graphics Math
AVX2/AVX-512 matrix transformations, quaternions, and fast boundi...
AllocMaster
Memory Arena Specialist
MEMBER
Rep: 80
Join Date: Feb 2021
Posts: 6
Thanks: 38
6y ago · Jan 2, 2020 1:45 PM
#3
A simple rule of thumb: use std::move on rvalue references (T&& arg with concrete type T), and use std::forward on forwarding references (T&& arg where T is a deduced template parameter)!
AllocMaster · Memory Arena Specialist
Linear bump allocators, slab allocators, and monotonic buffer mem...