Skip to content

Commit

Permalink
deploy: 010d6f3
Browse files Browse the repository at this point in the history
  • Loading branch information
archibate committed Nov 9, 2024
1 parent a9fc30e commit cc15160
Show file tree
Hide file tree
Showing 5 changed files with 96 additions and 28 deletions.
60 changes: 47 additions & 13 deletions auto/index.html
Original file line number Diff line number Diff line change
Expand Up @@ -256,7 +256,7 @@
<ul class="nav flex-column">
</ul>
</li>
<li class="nav-item" data-bs-level="2"><a href="#auto_4" class="nav-link">auto 推导为引用</a>
<li class="nav-item" data-bs-level="2"><a href="#auto_5" class="nav-link">auto 推导为引用</a>
<ul class="nav flex-column">
</ul>
</li>
Expand All @@ -279,31 +279,31 @@ <h2 id="auto_2">返回类型 <code>auto</code></h2>
<p><img src="../img/awesomeface.png" height="30px" width="auto" style="margin: 0; border: none"/> 闹了半天,还是要写返回类型,就只是挪到后面去好看一点……</p>
<p><img src="../img/question.png" height="30px" width="auto" style="margin: 0; border: none"/> 当初引入后置返回类型实际的用途是 <code>auto f(int x) -&gt; decltype(x * x) { return x * x; }</code> 这种情况,但很容易被接下来 C++14 引入的真正 <code>auto</code> 返回类型推导平替了。</p>
</blockquote>
<p>C++14 引入了函数<strong>返回类型推导</strong><code>auto</code> 才算真正意义上能用做函数返回类型,它会自动根据函数中的 <code>return</code> 表达式推导出函数的返回类型。</p>
<p>但是 C++14 引入了函数<strong>返回类型推导</strong><code>auto</code> 才算真正意义上能用做函数返回类型,它会自动根据函数中的 <code>return</code> 表达式推导出函数的返回类型。</p>
<pre><code class="language-cpp">auto f(int x) {
return x * x; // 表达式 `x * x` 的类型为 int,所以 auto 类型推导为 int
return x * x; // 表达式 `x * x` 的类型为 int,所以 auto 类型推导为 int
}
// 等价于:
int f() {
return x * x;
return x * x;
}
</code></pre>
<p>如果函数中没有 <code>return</code> 语句,那么 <code>auto</code> 会被自动推导为 <code>void</code>,非常方便。</p>
<pre><code class="language-cpp">auto f() {
std::println(&quot;hello&quot;);
std::println(&quot;hello&quot;);
}
// 等价于:
void f() {
std::println(&quot;hello&quot;);
std::println(&quot;hello&quot;);
}
</code></pre>
<p>值得注意的是,返回类型用 <code>auto</code> 来推导的函数,如果有多条 <code>return</code> 语句,那么他们必须都返回相同的类型,否则报错。</p>
<pre><code class="language-cpp">auto f(int x) {
if (x &gt; 0) {
return 1; // int
} else {
return 3.14; // double
}
if (x &gt; 0) {
return 1; // int
} else {
return 3.14; // double
}
} // 错误:有歧义,无法确定 auto 应该推导为 int 还是 double
</code></pre>
<p><code>auto</code> 还有一个缺点是,无法用于“分离声明和定义”的情况。因为推导 <code>auto</code> 类型需要知道函数体,才能看到里面的 <code>return</code> 表达式是什么类型。所以当 <code>auto</code> 返回类型被用于函数的非定义声明时,会直接报错。</p>
Expand All @@ -316,7 +316,41 @@ <h2 id="auto_2">返回类型 <code>auto</code></h2>
<p>因此,<code>auto</code> 通常只适用于头文件中“就地定义”的 <code>inline</code> 函数,不适合需要“分离 .cpp 文件”的函数。</p>
<h2 id="auto_3">参数类型 <code>auto</code></h2>
<p>C++20 引入了<strong>模板参数推导</strong>,可以让我们在函数参数中也使用 <code>auto</code></p>
<p>TODO: 介绍</p>
<p>在函数参数中也使用 <code>auto</code> 实际上等价于将该参数声明为模板参数,仅仅是一种更便捷的写法。</p>
<pre><code class="language-cpp">void func(auto x) {
std::cout &lt;&lt; x;
}
// 等价于:
template &lt;typename T&gt;
void func(T x) {
std::cout &lt;&lt; x;
}

func(1); // 自动推导为调用 func&lt;int&gt;(1)
func(3.14); // 自动推导为调用 func&lt;double&gt;(3.14)
</code></pre>
<p>如果参数类型的 <code>auto</code> 带有如 <code>auto &amp;</code> 这样的修饰,则实际上等价于相应模板函数的 <code>T &amp;</code></p>
<pre><code class="language-cpp">// 自动推导为常引用
void func(auto const &amp;x) {
std::cout &lt;&lt; x;
}
// 等价于:
template &lt;typename T&gt;
void func(T const &amp;x) {
std::cout &lt;&lt; x;
}

// 自动推导为万能引用
void func(auto &amp;&amp;x) {
std::cout &lt;&lt; x;
}
// 等价于:
template &lt;typename T&gt;
void func(T &amp;&amp;x) {
std::cout &lt;&lt; x;
}
</code></pre>
<h3 id="auto_4"><code>auto</code> 在多态中的妙用</h3>
<p>传统的,基于类型重载的:</p>
<pre><code class="language-cpp">int square(int x) {
return x * x;
Expand All @@ -343,7 +377,7 @@ <h2 id="auto_3">参数类型 <code>auto</code></h2>
// 即使未来产生了 float 版的需求,也不用添加任何代码,因为是 square 是很方便的模板函数
}
</code></pre>
<h2 id="auto_4"><code>auto</code> 推导为引用</h2>
<h2 id="auto_5"><code>auto</code> 推导为引用</h2>
<p>TODO: 继续介绍 <code>auto</code>, <code>auto const</code>, <code>auto &amp;</code>, <code>auto const &amp;</code>, <code>auto &amp;&amp;</code>, <code>decltype(auto)</code>, <code>auto *</code>, <code>auto const *</code></p></div>
</div>
</div>
Expand Down
2 changes: 1 addition & 1 deletion index.html
Original file line number Diff line number Diff line change
Expand Up @@ -292,7 +292,7 @@ <h2 id="_1">前言</h2>
<blockquote>
<p><img src="./img/bulb.png" height="30px" width="auto" style="margin: 0; border: none"/> 本书还在持续更新中……要追番的话,可以在 <a href="https://github.com/parallel101/cppguidebook">GitHub</a> 点一下右上角的 “Watch” 按钮,每当小彭老师提交新 commit,GitHub 会向你发送一封电子邮件,提醒你小彭老师更新了。</p>
</blockquote>
<p>更新时间:2024年11月01日 12:54:16 (UTC+08:00)</p>
<p>更新时间:2024年11月09日 11:37:54 (UTC+08:00)</p>
<p><a href="https://parallel101.github.io/cppguidebook">在 GitHub Pages 浏览本书</a> | <a href="https://142857.red/book">在小彭老师自己维护的镜像上浏览本书</a></p>
<h2 id="_2">格式约定</h2>
<blockquote>
Expand Down
60 changes: 47 additions & 13 deletions print_page/index.html
Original file line number Diff line number Diff line change
Expand Up @@ -421,7 +421,7 @@ <h2 id="index-_1">前言</h2>
<blockquote>
<p><img src="../img/bulb.png" height="30px" width="auto" style="margin: 0; border: none"/> 本书还在持续更新中……要追番的话,可以在 <a href="https://github.com/parallel101/cppguidebook">GitHub</a> 点一下右上角的 “Watch” 按钮,每当小彭老师提交新 commit,GitHub 会向你发送一封电子邮件,提醒你小彭老师更新了。</p>
</blockquote>
<p>更新时间:2024年11月01日 12:54:16 (UTC+08:00)</p>
<p>更新时间:2024年11月09日 11:37:54 (UTC+08:00)</p>
<p><a href="https://parallel101.github.io/cppguidebook">在 GitHub Pages 浏览本书</a> | <a href="https://142857.red/book">在小彭老师自己维护的镜像上浏览本书</a></p>
<h2 id="index-_2">格式约定</h2>
<blockquote>
Expand Down Expand Up @@ -941,31 +941,31 @@ <h2 id="auto-auto_2">返回类型 <code>auto</code></h2>
<p><img src="../img/awesomeface.png" height="30px" width="auto" style="margin: 0; border: none"/> 闹了半天,还是要写返回类型,就只是挪到后面去好看一点……</p>
<p><img src="../img/question.png" height="30px" width="auto" style="margin: 0; border: none"/> 当初引入后置返回类型实际的用途是 <code>auto f(int x) -&gt; decltype(x * x) { return x * x; }</code> 这种情况,但很容易被接下来 C++14 引入的真正 <code>auto</code> 返回类型推导平替了。</p>
</blockquote>
<p>C++14 引入了函数<strong>返回类型推导</strong>,<code>auto</code> 才算真正意义上能用做函数返回类型,它会自动根据函数中的 <code>return</code> 表达式推导出函数的返回类型。</p>
<p>但是 C++14 引入了函数<strong>返回类型推导</strong>,<code>auto</code> 才算真正意义上能用做函数返回类型,它会自动根据函数中的 <code>return</code> 表达式推导出函数的返回类型。</p>
<pre><code class="language-cpp">auto f(int x) {
return x * x; // 表达式 `x * x` 的类型为 int,所以 auto 类型推导为 int
return x * x; // 表达式 `x * x` 的类型为 int,所以 auto 类型推导为 int
}
// 等价于:
int f() {
return x * x;
return x * x;
}
</code></pre>
<p>如果函数中没有 <code>return</code> 语句,那么 <code>auto</code> 会被自动推导为 <code>void</code>,非常方便。</p>
<pre><code class="language-cpp">auto f() {
std::println(&quot;hello&quot;);
std::println(&quot;hello&quot;);
}
// 等价于:
void f() {
std::println(&quot;hello&quot;);
std::println(&quot;hello&quot;);
}
</code></pre>
<p>值得注意的是,返回类型用 <code>auto</code> 来推导的函数,如果有多条 <code>return</code> 语句,那么他们必须都返回相同的类型,否则报错。</p>
<pre><code class="language-cpp">auto f(int x) {
if (x &gt; 0) {
return 1; // int
} else {
return 3.14; // double
}
if (x &gt; 0) {
return 1; // int
} else {
return 3.14; // double
}
} // 错误:有歧义,无法确定 auto 应该推导为 int 还是 double
</code></pre>
<p><code>auto</code> 还有一个缺点是,无法用于“分离声明和定义”的情况。因为推导 <code>auto</code> 类型需要知道函数体,才能看到里面的 <code>return</code> 表达式是什么类型。所以当 <code>auto</code> 返回类型被用于函数的非定义声明时,会直接报错。</p>
Expand All @@ -978,7 +978,41 @@ <h2 id="auto-auto_2">返回类型 <code>auto</code></h2>
<p>因此,<code>auto</code> 通常只适用于头文件中“就地定义”的 <code>inline</code> 函数,不适合需要“分离 .cpp 文件”的函数。</p>
<h2 id="auto-auto_3">参数类型 <code>auto</code></h2>
<p>C++20 引入了<strong>模板参数推导</strong>,可以让我们在函数参数中也使用 <code>auto</code>。</p>
<p>TODO: 介绍</p>
<p>在函数参数中也使用 <code>auto</code> 实际上等价于将该参数声明为模板参数,仅仅是一种更便捷的写法。</p>
<pre><code class="language-cpp">void func(auto x) {
std::cout &lt;&lt; x;
}
// 等价于:
template &lt;typename T&gt;
void func(T x) {
std::cout &lt;&lt; x;
}

func(1); // 自动推导为调用 func&lt;int&gt;(1)
func(3.14); // 自动推导为调用 func&lt;double&gt;(3.14)
</code></pre>
<p>如果参数类型的 <code>auto</code> 带有如 <code>auto &amp;</code> 这样的修饰,则实际上等价于相应模板函数的 <code>T &amp;</code>。</p>
<pre><code class="language-cpp">// 自动推导为常引用
void func(auto const &amp;x) {
std::cout &lt;&lt; x;
}
// 等价于:
template &lt;typename T&gt;
void func(T const &amp;x) {
std::cout &lt;&lt; x;
}

// 自动推导为万能引用
void func(auto &amp;&amp;x) {
std::cout &lt;&lt; x;
}
// 等价于:
template &lt;typename T&gt;
void func(T &amp;&amp;x) {
std::cout &lt;&lt; x;
}
</code></pre>
<h3 id="auto-auto_4"><code>auto</code> 在多态中的妙用</h3>
<p>传统的,基于类型重载的:</p>
<pre><code class="language-cpp">int square(int x) {
return x * x;
Expand All @@ -1005,7 +1039,7 @@ <h2 id="auto-auto_3">参数类型 <code>auto</code></h2>
// 即使未来产生了 float 版的需求,也不用添加任何代码,因为是 square 是很方便的模板函数
}
</code></pre>
<h2 id="auto-auto_4"><code>auto</code> 推导为引用</h2>
<h2 id="auto-auto_5"><code>auto</code> 推导为引用</h2>
<p>TODO: 继续介绍 <code>auto</code>, <code>auto const</code>, <code>auto &amp;</code>, <code>auto const &amp;</code>, <code>auto &amp;&amp;</code>, <code>decltype(auto)</code>, <code>auto *</code>, <code>auto const *</code></p></section><section class="print-page" id="symbols"><h1 id="symbols-_1">重新认识声明与定义(未完工)</h1>
<div class="toc">
<ul>
Expand Down
2 changes: 1 addition & 1 deletion search/search_index.json

Large diffs are not rendered by default.

Binary file modified sitemap.xml.gz
Binary file not shown.

0 comments on commit cc15160

Please sign in to comment.