<?xml version="1.0" encoding="utf-8" standalone="yes"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:content="http://purl.org/rss/1.0/modules/content/">
  <channel>
    <title>移动语义与完美转发 on Dorkytiger 的小屋</title>
    <link>https://www.dorkytiger.top/c-plus-plus/stl-and-templates/01-move-semantics/</link>
    <description>Recent content in 移动语义与完美转发 on Dorkytiger 的小屋</description>
    <generator>Hugo</generator>
    <language>en-us</language>
    <atom:link href="https://www.dorkytiger.top/c-plus-plus/stl-and-templates/01-move-semantics/index.xml" rel="self" type="application/rss+xml" />
    <item>
      <title>一、 核心原理解释：物理视角的分类法</title>
      <link>https://www.dorkytiger.top/c-plus-plus/stl-and-templates/01-move-semantics/01-core-principles/</link>
      <pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate>
      <guid>https://www.dorkytiger.top/c-plus-plus/stl-and-templates/01-move-semantics/01-core-principles/</guid>
      <description>&lt;p&gt;在现代 C++ 中，一个表达式有两个独立维度的属性：&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;拥有身份（Has Identity）：在内存中有固定的、可寻址的物理地址。&lt;/li&gt;
&lt;li&gt;可被移动（Can be Moved）：生命周期即将结束，它的资源（比如堆内存）允许被别人无损接管。&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;根据这两个维度的组合，C++ 官方将所有的“值（Value）”严格划分为了三大主类：&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre tabindex=&#34;0&#34; style=&#34;color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4;-webkit-text-size-adjust:none;&#34;&gt;&lt;code class=&#34;language-text&#34; data-lang=&#34;text&#34;&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;                     ┌──────────────────┐
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;                     │   表达式（Value） │
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;                     └────────┬─────────┘
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;                              ▼
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;            ┌─────────────────┴─────────────────┐
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;            ▼                                   ▼
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;   【有身份 / 内存可寻址】                    【临时数据 / 可被移动】
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;      (Has Identity)                       (Can be Moved)
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;            │                                   │
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;      ┌─────┴───────────┐                 ┌─────┴───────────┐
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;      ▼                 ▼                 ▼                 ▼
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;   左值 (lvalue)    将亡值 (xvalue)   将亡值 (xvalue)   纯右值 (prvalue)
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;h3 id=&#34;1-左值-lvalue--有身份不可移动&#34;&gt;1. 左值 (lvalue) —— 有身份，不可移动&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;本质：指代一个持久存在的内存对象。只要你能用 &lt;code&gt;&amp;amp;&lt;/code&gt;（取地址符）拿到它在内存中的物理地址，它就是左值。&lt;/li&gt;
&lt;li&gt;特点：有名字，生命周期由作用域决定，编译器不能随意销毁它。&lt;/li&gt;
&lt;li&gt;常见示例：变量名 &lt;code&gt;a&lt;/code&gt;、函数名、左值引用 &lt;code&gt;int&amp;amp; r = a;&lt;/code&gt;、解引用表达式 &lt;code&gt;*ptr&lt;/code&gt;。&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 id=&#34;2-纯右值-prvalue--无身份可移动&#34;&gt;2. 纯右值 (prvalue) —— 无身份，可移动&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;本质：纯粹的临时字面量或运算产生的临时过渡数据。它们在物理内存中没有独立的持久身份（你没办法对它们取地址）。&lt;/li&gt;
&lt;li&gt;特点：没有名字，生命周期极短，通常只存在于 CPU 寄存器或编译器的临时栈帧中。&lt;/li&gt;
&lt;li&gt;常见示例：字面量 &lt;code&gt;42&lt;/code&gt;、&lt;code&gt;&#39;a&#39;&lt;/code&gt;；算术表达式 &lt;code&gt;a + b&lt;/code&gt;；函数返回的临时非引用对象（如 &lt;code&gt;std::string(&amp;quot;hello&amp;quot;)&lt;/code&gt;）。&lt;/li&gt;
&lt;/ul&gt;
&lt;h3 id=&#34;3-将亡值-xvalue--有身份可移动现代-c-零拷贝的精髓-&#34;&gt;3. 将亡值 (xvalue) —— 有身份，可移动（现代 C++ 零拷贝的精髓 ✨）&lt;/h3&gt;
&lt;ul&gt;
&lt;li&gt;本质：这是一个虽然在内存中有地址，但它马上就要被销毁（即将死亡）的对象。&lt;/li&gt;
&lt;li&gt;特点：因为它有身份，所以你可以找到它；因为它可移动，这意味着你被允许去“合法压榨”它，把它的堆内存指针据为己有。&lt;/li&gt;
&lt;li&gt;常见示例：最典型的将亡值就是通过 &lt;code&gt;std::move(a)&lt;/code&gt; 强转出来的结果，或者返回右值引用的函数调用。&lt;/li&gt;
&lt;/ul&gt;
&lt;hr&gt;</description>
    </item>
    <item>
      <title>二、 核心原理图：它们在内存中长什么样？</title>
      <link>https://www.dorkytiger.top/c-plus-plus/stl-and-templates/01-move-semantics/02-memory-layout/</link>
      <pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate>
      <guid>https://www.dorkytiger.top/c-plus-plus/stl-and-templates/01-move-semantics/02-memory-layout/</guid>
      <description>&lt;p&gt;我们用一段简单的 C++ 代码，画出它们在内存中的真实形态：&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre tabindex=&#34;0&#34; style=&#34;color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4;-webkit-text-size-adjust:none;&#34;&gt;&lt;code class=&#34;language-cpp&#34; data-lang=&#34;cpp&#34;&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;std&lt;span style=&#34;color:#f92672&#34;&gt;::&lt;/span&gt;string a &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;High Performance&amp;#34;&lt;/span&gt;;
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;std&lt;span style=&#34;color:#f92672&#34;&gt;::&lt;/span&gt;string b &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; a &lt;span style=&#34;color:#f92672&#34;&gt;+&lt;/span&gt; &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34; Log Server&amp;#34;&lt;/span&gt;; 
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;div class=&#34;highlight&#34;&gt;&lt;pre tabindex=&#34;0&#34; style=&#34;color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4;-webkit-text-size-adjust:none;&#34;&gt;&lt;code class=&#34;language-text&#34; data-lang=&#34;text&#34;&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;【 堆内存 (Heap) 】                 【 栈内存 (Stack) / 寄存器 】
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;┌───────────────────────┐            ┌────────────────────────┐
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;│ &amp;#34;High Performance&amp;#34;    │ ◄──────────┤ 变量名: a (左值 lvalue)  │ (能取地址 &amp;amp;a)
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;└───────────────────────┘            └────────────────────────┘
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;┌───────────────────────┐            ┌────────────────────────┐
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;│ &amp;#34;High Performance     │ ◄──────────┤ 临时变量 (纯右值 prvalue)│ (没名字, 没地址,
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;│  Log Server&amp;#34;          │            └────────────────────────┘  算完就扔)
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;└───────────────────────┘                        │
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;                                                 ▼ 拷贝赋值给
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;                                     ┌────────────────────────┐
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;                                     │ 变量名: b (左值 lvalue)  │ (能取地址 &amp;amp;b)
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;                                     └────────────────────────┘
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;hr&gt;</description>
    </item>
    <item>
      <title>三、 核心伪代码：编译器是怎么看它们的？</title>
      <link>https://www.dorkytiger.top/c-plus-plus/stl-and-templates/01-move-semantics/03-pseudocode/</link>
      <pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate>
      <guid>https://www.dorkytiger.top/c-plus-plus/stl-and-templates/01-move-semantics/03-pseudocode/</guid>
      <description>&lt;p&gt;如果我们要写一个接收不同值类型的函数，编译器在底层是通过不同的引用符号来重载和区分它们的：&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre tabindex=&#34;0&#34; style=&#34;color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4;-webkit-text-size-adjust:none;&#34;&gt;&lt;code class=&#34;language-text&#34; data-lang=&#34;text&#34;&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;函数 处理数据(左值引用 T&amp;amp; 变量) {
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    // 编译器说：传进来的是个正经左值（有名字、有地址）。
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    // 我必须小心翼翼地复制它，绝对不能破坏原数据！
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    执行深拷贝(变量);
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;}
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;函数 处理数据(右值引用 T&amp;amp;&amp;amp; 变量) {
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    // 编译器说：传进来的是个右值（纯右值或将亡值，反正它马上要死了）。
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    // 太好了！我可以合法当劫匪，直接偷走它的堆内存指针！
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    执行零拷贝所有权转移(变量);
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;}
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;hr&gt;</description>
    </item>
    <item>
      <title>四、 参考代码：亲自手写验证 Demo</title>
      <link>https://www.dorkytiger.top/c-plus-plus/stl-and-templates/01-move-semantics/04-demo-code/</link>
      <pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate>
      <guid>https://www.dorkytiger.top/c-plus-plus/stl-and-templates/01-move-semantics/04-demo-code/</guid>
      <description>&lt;p&gt;请在一个独立的 &lt;code&gt;01_value_types.cpp&lt;/code&gt; 中手写并运行以下代码（使用 &lt;code&gt;g++ 01_value_types.cpp -o value_types&lt;/code&gt; 编译）。这个 Demo 会用最直观的编译行为，向你展示编译器对这几种值类型的精准判定。&lt;/p&gt;
&lt;div class=&#34;highlight&#34;&gt;&lt;pre tabindex=&#34;0&#34; style=&#34;color:#f8f8f2;background-color:#272822;-moz-tab-size:4;-o-tab-size:4;tab-size:4;-webkit-text-size-adjust:none;&#34;&gt;&lt;code class=&#34;language-cpp&#34; data-lang=&#34;cpp&#34;&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;&lt;span style=&#34;color:#75715e&#34;&gt;#include&lt;/span&gt; &lt;span style=&#34;color:#75715e&#34;&gt;&amp;lt;iostream&amp;gt;&lt;/span&gt;&lt;span style=&#34;color:#75715e&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;&lt;span style=&#34;color:#75715e&#34;&gt;#include&lt;/span&gt; &lt;span style=&#34;color:#75715e&#34;&gt;&amp;lt;string&amp;gt;&lt;/span&gt;&lt;span style=&#34;color:#75715e&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;&lt;span style=&#34;color:#75715e&#34;&gt;#include&lt;/span&gt; &lt;span style=&#34;color:#75715e&#34;&gt;&amp;lt;utility&amp;gt;&lt;/span&gt;&lt;span style=&#34;color:#75715e&#34;&gt;
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;&lt;span style=&#34;color:#75715e&#34;&gt;// 重载函数 A：专门接收左值
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;&lt;span style=&#34;color:#66d9ef&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#a6e22e&#34;&gt;GetValueType&lt;/span&gt;(&lt;span style=&#34;color:#66d9ef&#34;&gt;int&lt;/span&gt;&lt;span style=&#34;color:#f92672&#34;&gt;&amp;amp;&lt;/span&gt; lref) {
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    std&lt;span style=&#34;color:#f92672&#34;&gt;::&lt;/span&gt;cout &lt;span style=&#34;color:#f92672&#34;&gt;&amp;lt;&amp;lt;&lt;/span&gt; &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;🧱 编译器判定：这是一个【左值 lvalue】(有固定内存地址)&lt;/span&gt;&lt;span style=&#34;color:#ae81ff&#34;&gt;\n&lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;&lt;/span&gt;;
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;}
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;&lt;span style=&#34;color:#75715e&#34;&gt;// 重载函数 B：专门接收右值（包括纯右值和将亡值）
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;&lt;span style=&#34;color:#66d9ef&#34;&gt;void&lt;/span&gt; &lt;span style=&#34;color:#a6e22e&#34;&gt;GetValueType&lt;/span&gt;(&lt;span style=&#34;color:#66d9ef&#34;&gt;int&lt;/span&gt;&lt;span style=&#34;color:#f92672&#34;&gt;&amp;amp;&amp;amp;&lt;/span&gt; rref) {
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    std&lt;span style=&#34;color:#f92672&#34;&gt;::&lt;/span&gt;cout &lt;span style=&#34;color:#f92672&#34;&gt;&amp;lt;&amp;lt;&lt;/span&gt; &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;🚀 编译器判定：这是一个【右值】(无地址的纯右值 或 允许被压榨的将亡值)&lt;/span&gt;&lt;span style=&#34;color:#ae81ff&#34;&gt;\n&lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;&lt;/span&gt;;
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;}
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;&lt;span style=&#34;color:#66d9ef&#34;&gt;int&lt;/span&gt; &lt;span style=&#34;color:#a6e22e&#34;&gt;GetTemporaryInt&lt;/span&gt;() {
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    &lt;span style=&#34;color:#66d9ef&#34;&gt;return&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;100&lt;/span&gt;; &lt;span style=&#34;color:#75715e&#34;&gt;// 返回一个临时值（纯右值）
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;}
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;&lt;span style=&#34;color:#66d9ef&#34;&gt;int&lt;/span&gt; &lt;span style=&#34;color:#a6e22e&#34;&gt;main&lt;/span&gt;() {
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    std&lt;span style=&#34;color:#f92672&#34;&gt;::&lt;/span&gt;cout &lt;span style=&#34;color:#f92672&#34;&gt;&amp;lt;&amp;lt;&lt;/span&gt; &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;--- 开始 C++11 值类型硬核验证 ---&lt;/span&gt;&lt;span style=&#34;color:#ae81ff&#34;&gt;\n\n&lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;&lt;/span&gt;;
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    &lt;span style=&#34;color:#75715e&#34;&gt;// 1. 验证左值
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    &lt;span style=&#34;color:#66d9ef&#34;&gt;int&lt;/span&gt; x &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;42&lt;/span&gt;; 
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    GetValueType(x); &lt;span style=&#34;color:#75715e&#34;&gt;// x 是个正经变量，有名字，能取地址 &amp;amp;x ➔ 触发左值重载
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    &lt;span style=&#34;color:#75715e&#34;&gt;// 2. 验证纯右值 (prvalue)
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    GetValueType(&lt;span style=&#34;color:#ae81ff&#34;&gt;42&lt;/span&gt;);                &lt;span style=&#34;color:#75715e&#34;&gt;// 42 是字面量，没名字没地址 ➔ 触发右值重载
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    GetValueType(GetTemporaryInt()); &lt;span style=&#34;color:#75715e&#34;&gt;// 函数返回的临时 100，算完就消失 ➔ 触发右值重载
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    &lt;span style=&#34;color:#75715e&#34;&gt;// 3. 验证将亡值 (xvalue)
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    &lt;span style=&#34;color:#75715e&#34;&gt;// std::move 并没有移动任何东西，它的本质就是把左值 x，强制类型转换成【将亡值】！
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    &lt;span style=&#34;color:#75715e&#34;&gt;// 告诉编译器：“这个 x 我以后不用了，它马上要死了，你可以随时移走它的资源！”
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    GetValueType(std&lt;span style=&#34;color:#f92672&#34;&gt;::&lt;/span&gt;move(x)); &lt;span style=&#34;color:#75715e&#34;&gt;// 强转出来的将亡值 ➔ 触发右值重载
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    &lt;span style=&#34;color:#75715e&#34;&gt;// 4. 深度思考：右值引用变量本身，是什么值？
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    &lt;span style=&#34;color:#66d9ef&#34;&gt;int&lt;/span&gt;&lt;span style=&#34;color:#f92672&#34;&gt;&amp;amp;&amp;amp;&lt;/span&gt; ref &lt;span style=&#34;color:#f92672&#34;&gt;=&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;100&lt;/span&gt;; &lt;span style=&#34;color:#75715e&#34;&gt;// ref 是一个右值引用，绑定了右值 100
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    &lt;span style=&#34;color:#75715e&#34;&gt;// 🚨 思考：把 ref 传给 GetValueType，会触发哪个？
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    &lt;span style=&#34;color:#75715e&#34;&gt;// 答案是左值！因为 ref 这个“名字”本身是一直持久存在的，你能对 &amp;amp;ref 取地址！
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    std&lt;span style=&#34;color:#f92672&#34;&gt;::&lt;/span&gt;cout &lt;span style=&#34;color:#f92672&#34;&gt;&amp;lt;&amp;lt;&lt;/span&gt; &lt;span style=&#34;color:#e6db74&#34;&gt;&amp;#34;&lt;/span&gt;&lt;span style=&#34;color:#ae81ff&#34;&gt;\n&lt;/span&gt;&lt;span style=&#34;color:#e6db74&#34;&gt;【终极陷阱测试】: &amp;#34;&lt;/span&gt;;
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    GetValueType(ref); &lt;span style=&#34;color:#75715e&#34;&gt;// ➔ 触发左值重载！
&lt;/span&gt;&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;    &lt;span style=&#34;color:#66d9ef&#34;&gt;return&lt;/span&gt; &lt;span style=&#34;color:#ae81ff&#34;&gt;0&lt;/span&gt;;
&lt;/span&gt;&lt;/span&gt;&lt;span style=&#34;display:flex;&#34;&gt;&lt;span&gt;}
&lt;/span&gt;&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;&lt;hr&gt;</description>
    </item>
    <item>
      <title>💡 记录到笔记的通关口诀（用于面试一秒作答）</title>
      <link>https://www.dorkytiger.top/c-plus-plus/stl-and-templates/01-move-semantics/05-mnemonic/</link>
      <pubDate>Mon, 01 Jan 0001 00:00:00 +0000</pubDate>
      <guid>https://www.dorkytiger.top/c-plus-plus/stl-and-templates/01-move-semantics/05-mnemonic/</guid>
      <description>&lt;ol&gt;
&lt;li&gt;左值 (lvalue)：有名、有固定地址，生命周期长，只能复制，不能偷。&lt;/li&gt;
&lt;li&gt;纯右值 (prvalue)：无名、无固定地址（临时工），生命周期极短，可以直接偷。&lt;/li&gt;
&lt;li&gt;将亡值 (xvalue)：有名、有固定地址，但被人用 &lt;code&gt;std::move&lt;/code&gt; 盖上了“即将死亡”的戳，属于合法允许被偷的左值。&lt;/li&gt;
&lt;/ol&gt;
&lt;h2 id=&#34;多看一眼上面的第-4-点终极陷阱测试这是大厂面试如腾讯网易游戏极度爱考的变态细节右值引用变量本身其实是一个左值&#34;&gt;多看一眼上面的第 4 点（终极陷阱测试），这是大厂面试（如腾讯、网易游戏）极度爱考的变态细节：“右值引用变量本身，其实是一个左值”。&lt;/h2&gt;</description>
    </item>
  </channel>
</rss>
