Challenge 3: What std::move Actually Does at the Type-System Level — Possible Solution ==================================================================== Per the chapter, std::move performs NO runtime action of its own whatsoever -- it doesn't copy anything, doesn't null anything out, doesn't touch the object's data in any way. What it actually does, purely at the TYPE-SYSTEM level, is CHANGE THE COMPILE-TIME CLASSIFICATION of the expression it's applied to: given an lvalue (a named variable, which the compiler would otherwise treat as binding to a T& parameter, selecting a copy constructor/assignment), std::move produces an rvalue reference (T&&) referring to that SAME object. It's essentially a cast -- specifically an unconditional cast to an rvalue reference type -- and nothing more. The object itself is completely unchanged by the call to std::move alone; only how the COMPILER subsequently treats that expression, for the purpose of overload resolution, has changed. What actually causes the move constructor to run afterward is ordinary C++ OVERLOAD RESOLUTION, per cpp1-3's own material: once an expression has been cast to an rvalue reference type, the compiler looks for the best-matching overload among the target type's available constructors (or assignment operators). A class that has defined a move constructor taking Buffer&& (or the built-in generated one, if eligible) is now a better, more specific match for an rvalue-reference argument than the copy constructor taking a plain Buffer&, so the compiler selects the MOVE constructor for the actual construction of the new object. It is this constructor CALL -- triggered by ordinary overload resolution choosing the best match for the now-rvalue-typed expression -- that performs the real work of copying the pointer and nulling out the source, exactly as the chapter's own Buffer example does. WHY THIS WORKS AS AN ANSWER ------------------------------ This precisely separates what std::move itself does (a compile-time cast, changing an expression's value category, nothing more) from what actually performs the real work (the move constructor, selected via ordinary overload resolution once the cast makes it the best match) -- rather than conflating the two into "std::move moves the object."