List of Sort - text.Baldanders.info
tag:text.Baldanders.info,2020-09-07:/tags
2020-09-07T11:16:53+09:00
帰ってきた「しっぽのさきっちょ」
https://text.baldanders.info/images/avatar.jpg
https://text.baldanders.info/images/avatar.jpg
time.Time の比較が覚えれん!
tag:text.Baldanders.info,2020-09-07:/golang/order-by-time/
2020-09-07T02:16:53+00:00
2021-12-04T02:40:05+00:00
一覧表にしておこう。
Spiegel
https://baldanders.info/profile/
<p>時刻を表す <a href="https://pkg.go.dev/time" title="time package · pkg.go.dev"><code>time</code></a><code>.Time</code> 型は比較演算子(<code>==</code>, <code><</code>, <code>></code> 等)が使えないので <code>Equal()</code>, <code>Before()</code>, <code>After()</code> 各メソッドが用意されているのだけど, <code>Equal()</code> メソッドはともかく <code>Before()</code> や <code>After()</code> は覚えれんっちうの!</p>
<p>まぁ<a href="https://pkg.go.dev/time" title="time package · pkg.go.dev">ドキュメント</a>を見れば済む話なのだが,毎回「どうだっけ?」と探すのもナニなので,この際,記事として纏めておくことにした。</p>
<p>まずはコードを書いてみる。
これ基本。</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-go" data-lang="go"><span class="line"><span class="cl"><span class="kn">package</span> <span class="nx">main</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="kn">import</span> <span class="p">(</span>
</span></span><span class="line"><span class="cl"> <span class="s">"fmt"</span>
</span></span><span class="line"><span class="cl"> <span class="s">"time"</span>
</span></span><span class="line"><span class="cl"><span class="p">)</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="kd">func</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">year2000</span> <span class="o">:=</span> <span class="nx">time</span><span class="p">.</span><span class="nf">Date</span><span class="p">(</span><span class="mi">2000</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="nx">time</span><span class="p">.</span><span class="nx">UTC</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"> <span class="nx">year3000</span> <span class="o">:=</span> <span class="nx">time</span><span class="p">.</span><span class="nf">Date</span><span class="p">(</span><span class="mi">3000</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="nx">time</span><span class="p">.</span><span class="nx">UTC</span><span class="p">)</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"> <span class="nx">fmt</span><span class="p">.</span><span class="nf">Printf</span><span class="p">(</span><span class="s">"year3000.After(year2000) = %v\n"</span><span class="p">,</span> <span class="nx">year3000</span><span class="p">.</span><span class="nf">After</span><span class="p">(</span><span class="nx">year2000</span><span class="p">))</span>
</span></span><span class="line"><span class="cl"> <span class="nx">fmt</span><span class="p">.</span><span class="nf">Printf</span><span class="p">(</span><span class="s">"year3000.Before(year2000) = %v\n"</span><span class="p">,</span> <span class="nx">year3000</span><span class="p">.</span><span class="nf">Before</span><span class="p">(</span><span class="nx">year2000</span><span class="p">))</span>
</span></span><span class="line"><span class="cl"> <span class="nx">fmt</span><span class="p">.</span><span class="nf">Printf</span><span class="p">(</span><span class="s">"year2000.After(year3000) = %v\n"</span><span class="p">,</span> <span class="nx">year2000</span><span class="p">.</span><span class="nf">After</span><span class="p">(</span><span class="nx">year3000</span><span class="p">))</span>
</span></span><span class="line"><span class="cl"> <span class="nx">fmt</span><span class="p">.</span><span class="nf">Printf</span><span class="p">(</span><span class="s">"year2000.Before(year3000) = %v\n"</span><span class="p">,</span> <span class="nx">year2000</span><span class="p">.</span><span class="nf">Before</span><span class="p">(</span><span class="nx">year3000</span><span class="p">))</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span></code></pre></div><p>これの実行結果は</p>
<pre tabindex="0"><code class="language-test" data-lang="test">$ go run sample1.go
year3000.After(year2000) = true
year3000.Before(year2000) = false
year2000.After(year3000) = false
year2000.Before(year3000) = true
</code></pre><p>となる。
<code>a.After(b)</code> は「<code>a</code> は <code>b</code> の後か?」と覚えればいいかな。</p>
<p>やっぱ面倒くさい。
一覧表にしておこう。</p>
<figure style='margin:0 auto;text-align:center;'>
<table class="left">
<thead><tr>
<th>関係</th>
<th>メソッド</th>
<th>返り値</th>
</tr></thead>
<tbody>
<tr><td class="center" rowspan="3" style="vertical-align:middle;">$a = b$</td>
<td><code>a.Equal(b)</code></td><td class="center"><code>true</code></td></tr>
<tr><td><code>a.Before(b)</code></td><td class="center"><code>false</code></td></tr>
<tr><td><code>a.After(b)</code></td><td class="center"><code>false</code></td></tr>
<tr><td class="center" rowspan="3" style="vertical-align:middle;">$a \lt b$</td>
<td><code>a.Equal(b)</code></td><td class="center"><code>false</code></td></tr>
<tr><td><code>a.Before(b)</code></td><td class="center"><code>true</code></td></tr>
<tr><td><code>a.After(b)</code></td><td class="center"><code>false</code></td></tr>
<tr><td class="center" rowspan="3" style="vertical-align:middle;">$a \gt b$</td>
<td><code>a.Equal(b)</code></td><td class="center"><code>false</code></td></tr>
<tr><td><code>a.Before(b)</code></td><td class="center"><code>false</code></td></tr>
<tr><td><code>a.After(b)</code></td><td class="center"><code>true</code></td></tr>
</tbody>
</table>
</figure>
<h2>【サンプル】時刻のソート</h2>
<p>もう少し「ありそう」なサンプルを考えてみよう。
たとえば,以下のようなデータセット <code>eraList</code> があるとする。</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-go" data-lang="go"><span class="line"><span class="cl"><span class="kd">type</span> <span class="nx">Era</span> <span class="kd">struct</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">Name</span> <span class="kt">string</span>
</span></span><span class="line"><span class="cl"> <span class="nx">Start</span> <span class="nx">time</span><span class="p">.</span><span class="nx">Time</span>
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="kd">var</span> <span class="p">(</span>
</span></span><span class="line"><span class="cl"> <span class="nx">jst</span> <span class="p">=</span> <span class="nx">time</span><span class="p">.</span><span class="nf">FixedZone</span><span class="p">(</span><span class="s">"JST"</span><span class="p">,</span> <span class="mi">9</span><span class="o">*</span><span class="mi">60</span><span class="o">*</span><span class="mi">60</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"> <span class="nx">eraList</span> <span class="p">=</span> <span class="p">[]</span><span class="nx">Era</span><span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="p">{</span><span class="nx">Name</span><span class="p">:</span> <span class="s">"令和"</span><span class="p">,</span> <span class="nx">Start</span><span class="p">:</span> <span class="nx">time</span><span class="p">.</span><span class="nf">Date</span><span class="p">(</span><span class="mi">2019</span><span class="p">,</span> <span class="nx">time</span><span class="p">.</span><span class="nx">May</span><span class="p">,</span> <span class="mi">1</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="nx">jst</span><span class="p">)},</span>
</span></span><span class="line"><span class="cl"> <span class="p">{</span><span class="nx">Name</span><span class="p">:</span> <span class="s">"平成"</span><span class="p">,</span> <span class="nx">Start</span><span class="p">:</span> <span class="nx">time</span><span class="p">.</span><span class="nf">Date</span><span class="p">(</span><span class="mi">1989</span><span class="p">,</span> <span class="nx">time</span><span class="p">.</span><span class="nx">January</span><span class="p">,</span> <span class="mi">8</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="nx">jst</span><span class="p">)},</span>
</span></span><span class="line"><span class="cl"> <span class="p">{</span><span class="nx">Name</span><span class="p">:</span> <span class="s">"昭和"</span><span class="p">,</span> <span class="nx">Start</span><span class="p">:</span> <span class="nx">time</span><span class="p">.</span><span class="nf">Date</span><span class="p">(</span><span class="mi">1926</span><span class="p">,</span> <span class="nx">time</span><span class="p">.</span><span class="nx">December</span><span class="p">,</span> <span class="mi">25</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="nx">jst</span><span class="p">)},</span>
</span></span><span class="line"><span class="cl"> <span class="p">{</span><span class="nx">Name</span><span class="p">:</span> <span class="s">"大正"</span><span class="p">,</span> <span class="nx">Start</span><span class="p">:</span> <span class="nx">time</span><span class="p">.</span><span class="nf">Date</span><span class="p">(</span><span class="mi">1912</span><span class="p">,</span> <span class="nx">time</span><span class="p">.</span><span class="nx">July</span><span class="p">,</span> <span class="mi">30</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="nx">jst</span><span class="p">)},</span>
</span></span><span class="line"><span class="cl"> <span class="p">}</span>
</span></span><span class="line"><span class="cl"><span class="p">)</span>
</span></span></code></pre></div><p>この <code>eraList</code> を時刻の昇順で並べ替えてみる。
こんな感じかな。</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-go" data-lang="go"><span class="line"><span class="cl"><span class="kd">func</span> <span class="p">(</span><span class="nx">e</span> <span class="nx">Era</span><span class="p">)</span> <span class="nf">String</span><span class="p">()</span> <span class="kt">string</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="k">return</span> <span class="nx">fmt</span><span class="p">.</span><span class="nf">Sprintf</span><span class="p">(</span><span class="s">"%s (from %s)"</span><span class="p">,</span> <span class="nx">e</span><span class="p">.</span><span class="nx">Name</span><span class="p">,</span> <span class="nx">e</span><span class="p">.</span><span class="nx">Start</span><span class="p">.</span><span class="nf">Format</span><span class="p">(</span><span class="s">"2006-01-02"</span><span class="p">))</span>
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="kd">func</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">fmt</span><span class="p">.</span><span class="nf">Println</span><span class="p">(</span><span class="nx">eraList</span><span class="p">)</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"> <span class="nx">sort</span><span class="p">.</span><span class="nf">Slice</span><span class="p">(</span><span class="nx">eraList</span><span class="p">,</span> <span class="kd">func</span><span class="p">(</span><span class="nx">i</span><span class="p">,</span> <span class="nx">j</span> <span class="kt">int</span><span class="p">)</span> <span class="kt">bool</span> <span class="p">{</span>
</span></span><span class="line hl"><span class="cl"> <span class="k">return</span> <span class="nx">eraList</span><span class="p">[</span><span class="nx">i</span><span class="p">].</span><span class="nx">Start</span><span class="p">.</span><span class="nf">Before</span><span class="p">(</span><span class="nx">eraList</span><span class="p">[</span><span class="nx">j</span><span class="p">].</span><span class="nx">Start</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"> <span class="p">})</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"> <span class="nx">fmt</span><span class="p">.</span><span class="nf">Println</span><span class="p">(</span><span class="nx">eraList</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span></code></pre></div><p>結果は以下の通り。</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-text" data-lang="text"><span class="line"><span class="cl">$ go run sample2.go
</span></span><span class="line"><span class="cl">[令和 (from 2019-05-01) 平成 (from 1989-01-08) 昭和 (from 1926-12-25) 大正 (from 1912-07-30)]
</span></span><span class="line"><span class="cl">[大正 (from 1912-07-30) 昭和 (from 1926-12-25) 平成 (from 1989-01-08) 令和 (from 2019-05-01)]
</span></span></code></pre></div><p>よーし,うむうむ,よーし。</p>
<h2>参考図書</h2>
<div class="hreview">
<div class="photo"><a href="https://www.amazon.co.jp/dp/B099928SJD?tag=baldandersinf-22&linkCode=ogi&th=1&psc=1"><img src="https://m.media-amazon.com/images/I/416Stewy0NS._SL160_.jpg" width="123" alt="photo"></a></div>
<dl>
<dt class="item"><a class="fn url" href="https://www.amazon.co.jp/dp/B099928SJD?tag=baldandersinf-22&linkCode=ogi&th=1&psc=1">プログラミング言語Go</a></dt>
<dd>アラン・ドノバン (著), ブライアン・カーニハン (著), 柴田芳樹 (著)</dd>
<dd>丸善出版 2016-06-20 (Release 2021-07-13)</dd>
<dd>Kindle版</dd>
<dd>B099928SJD (ASIN)</dd>
<dd>評価<abbr class="rating fa-sm" title="5"> <i class="fas fa-star"></i> <i class="fas fa-star"></i> <i class="fas fa-star"></i> <i class="fas fa-star"></i> <i class="fas fa-star"></i></abbr></dd>
</dl>
<p class="description">Kindle 版出た! 一部内容が古びてしまったが,この本は Go 言語の教科書と言ってもいいだろう。感想は<a href="https://text.baldanders.info/remark/2016/07/go-programming-language/" >こちら</a>。</p>
<p class="powered-by">reviewed by <a href='#maker' class='reviewer'>Spiegel</a> on <abbr class="dtreviewed" title="2021-05-22">2021-05-22</abbr> (powered by <a href="https://affiliate.amazon.co.jp/assoc_credentials/home">PA-APIv5</a>)</p>
</div> <!-- プログラミング言語Go -->
ソートを使う
tag:text.Baldanders.info,2017-04-07:/golang/sort/
2017-04-07T11:01:34+00:00
2023-08-10T08:20:29+00:00
ソートをアルゴリズムまで言及すると非常に深いテーマになるのだが,今回は標準の sort パッケージの使い方に絞って「こんな感じ」で説明していく。
Spiegel
https://baldanders.info/profile/
<p>今回はソート(sort)のお話。</p>
<p>プログラマでソートを知らない人はいないだろうが,一応説明しておくと,あるデータの集合を一定の規則に従って並べ替えることを指す。
日本語では「整列」と呼んだりするらしい。
ソートをアルゴリズムまで言及すると非常に深いテーマになるのだが,今回は標準の <a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a> パッケージの使い方に絞って「こんな感じ」で説明していく。</p>
<p>なお,この記事で紹介するコードは <a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a> パッケージのドキュメントに書かれているものを流用している。
<a href="https://go.dev/" title="The Go Programming Language">Go 言語</a>のコンパイラ・コードは MIT ライセンスで提供されているのでご注意を。</p>
<h2>基本型データ列のソート</h2>
<p><a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a> パッケージでは基本型の int, float64, string についてはソート関数が用意されている。</p>
<p>たとえば <code>{0.055, 0.815, 1.0, 0.107}</code> というデータ列があるとしよう。
これを昇順(小さい値から大きい値へ順に並べること)で並べることを考える。
この場合は <a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a><code>.Float64s()</code> 関数を使えば簡単である。
コードにするとこんな感じ。</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-go" data-lang="go"><span class="line"><span class="cl"><span class="kn">package</span> <span class="nx">main</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="kn">import</span> <span class="p">(</span>
</span></span><span class="line"><span class="cl"> <span class="s">"fmt"</span>
</span></span><span class="line"><span class="cl"> <span class="s">"sort"</span>
</span></span><span class="line"><span class="cl"><span class="p">)</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="kd">func</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">fset</span> <span class="o">:=</span> <span class="p">[]</span><span class="kt">float64</span><span class="p">{</span><span class="mf">0.055</span><span class="p">,</span> <span class="mf">0.815</span><span class="p">,</span> <span class="mf">1.0</span><span class="p">,</span> <span class="mf">0.107</span><span class="p">}</span>
</span></span><span class="line"><span class="cl"> <span class="k">for</span> <span class="nx">_</span><span class="p">,</span> <span class="nx">f</span> <span class="o">:=</span> <span class="k">range</span> <span class="nx">fset</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">fmt</span><span class="p">.</span><span class="nf">Printf</span><span class="p">(</span><span class="s">"%f "</span><span class="p">,</span> <span class="nx">f</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"> <span class="p">}</span>
</span></span><span class="line"><span class="cl"> <span class="nx">fmt</span><span class="p">.</span><span class="nf">Print</span><span class="p">(</span><span class="s">"\n"</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"> <span class="nx">sort</span><span class="p">.</span><span class="nf">Float64s</span><span class="p">(</span><span class="nx">fset</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"> <span class="k">for</span> <span class="nx">_</span><span class="p">,</span> <span class="nx">f</span> <span class="o">:=</span> <span class="k">range</span> <span class="nx">fset</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">fmt</span><span class="p">.</span><span class="nf">Printf</span><span class="p">(</span><span class="s">"%f "</span><span class="p">,</span> <span class="nx">f</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"> <span class="p">}</span>
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span></code></pre></div><p>結果はこんな感じになる。</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-text" data-lang="text"><span class="line"><span class="cl">$ go run sort1.go
</span></span><span class="line"><span class="cl">0.055000 0.815000 1.000000 0.107000
</span></span><span class="line"><span class="cl">0.055000 0.107000 0.815000 1.000000
</span></span></code></pre></div><p>では,降順(大きい値から小さい値へ順に並べること)で並べるにはどうすればいいだろう。
これはちょっとだけ面倒くさくなる。</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-go" data-lang="go"><span class="line"><span class="cl"><span class="kn">package</span> <span class="nx">main</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="kn">import</span> <span class="p">(</span>
</span></span><span class="line"><span class="cl"> <span class="s">"fmt"</span>
</span></span><span class="line"><span class="cl"> <span class="s">"sort"</span>
</span></span><span class="line"><span class="cl"><span class="p">)</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="kd">func</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">fset</span> <span class="o">:=</span> <span class="p">[]</span><span class="kt">float64</span><span class="p">{</span><span class="mf">0.055</span><span class="p">,</span> <span class="mf">0.815</span><span class="p">,</span> <span class="mf">1.0</span><span class="p">,</span> <span class="mf">0.107</span><span class="p">}</span>
</span></span><span class="line"><span class="cl"> <span class="k">for</span> <span class="nx">_</span><span class="p">,</span> <span class="nx">f</span> <span class="o">:=</span> <span class="k">range</span> <span class="nx">fset</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">fmt</span><span class="p">.</span><span class="nf">Printf</span><span class="p">(</span><span class="s">"%f "</span><span class="p">,</span> <span class="nx">f</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"> <span class="p">}</span>
</span></span><span class="line"><span class="cl"> <span class="nx">fmt</span><span class="p">.</span><span class="nf">Print</span><span class="p">(</span><span class="s">"\n"</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"> <span class="nx">sort</span><span class="p">.</span><span class="nf">Sort</span><span class="p">(</span><span class="nx">sort</span><span class="p">.</span><span class="nf">Reverse</span><span class="p">(</span><span class="nx">sort</span><span class="p">.</span><span class="nf">Float64Slice</span><span class="p">(</span><span class="nx">fset</span><span class="p">)))</span>
</span></span><span class="line"><span class="cl"> <span class="k">for</span> <span class="nx">_</span><span class="p">,</span> <span class="nx">f</span> <span class="o">:=</span> <span class="k">range</span> <span class="nx">fset</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">fmt</span><span class="p">.</span><span class="nf">Printf</span><span class="p">(</span><span class="s">"%f "</span><span class="p">,</span> <span class="nx">f</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"> <span class="p">}</span>
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span></code></pre></div><p>まず <a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a><code>.Float64Slice</code> は <code>[]float64</code> を示す型である。</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-go" data-lang="go"><span class="line"><span class="cl"><span class="kd">type</span> <span class="nx">Float64Slice</span> <span class="p">[]</span><span class="kt">float64</span>
</span></span></code></pre></div><p>この型が示すデータ集合を <a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a><code>.Sort()</code> 関数で並べ替えるのだが,並べ替えの規則を <a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a><code>.Reverse()</code> 関数で反転させている。
実行結果はこんな感じでちゃんと降順になっているのが分かるだろう。</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-text" data-lang="text"><span class="line"><span class="cl">$ go run sort2.go
</span></span><span class="line"><span class="cl">0.055000 0.815000 1.000000 0.107000
</span></span><span class="line"><span class="cl">1.000000 0.815000 0.107000 0.055000
</span></span></code></pre></div><p>実は最初に出た <a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a><code>.Float64s()</code> 関数は内部で <a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a><code>.Sort()</code> 関数を呼んでいる。</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-go" data-lang="go"><span class="line"><span class="cl"><span class="c1">// Float64s sorts a slice of float64s in increasing order.
</span></span></span><span class="line"><span class="cl"><span class="c1"></span><span class="kd">func</span> <span class="nf">Float64s</span><span class="p">(</span><span class="nx">a</span> <span class="p">[]</span><span class="kt">float64</span><span class="p">)</span> <span class="p">{</span> <span class="nf">Sort</span><span class="p">(</span><span class="nf">Float64Slice</span><span class="p">(</span><span class="nx">a</span><span class="p">))</span> <span class="p">}</span>
</span></span></code></pre></div><p>で, <a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a><code>.Sort()</code> 関数の内部では <a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a><code>.Float64Slice</code> に紐付く <code>Len()</code>, <code>Less()</code>, <code>Swap()</code> 各メソッドが呼ばれている。
<code>Len()</code>, <code>Less()</code>, <code>Swap()</code> 各メソッドを持つ <a href="https://go.dev/doc/effective_go#interfaces_and_types" title="Effective Go - The Go Programming Language">interface</a> は以下のように定義されている。</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-go" data-lang="go"><span class="line"><span class="cl"><span class="c1">// A type, typically a collection, that satisfies sort.Interface can be
</span></span></span><span class="line"><span class="cl"><span class="c1">// sorted by the routines in this package. The methods require that the
</span></span></span><span class="line"><span class="cl"><span class="c1">// elements of the collection be enumerated by an integer index.
</span></span></span><span class="line"><span class="cl"><span class="c1"></span><span class="kd">type</span> <span class="nx">Interface</span> <span class="kd">interface</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="c1">// Len is the number of elements in the collection.
</span></span></span><span class="line"><span class="cl"><span class="c1"></span> <span class="nf">Len</span><span class="p">()</span> <span class="kt">int</span>
</span></span><span class="line"><span class="cl"> <span class="c1">// Less reports whether the element with
</span></span></span><span class="line"><span class="cl"><span class="c1"></span> <span class="c1">// index i should sort before the element with index j.
</span></span></span><span class="line"><span class="cl"><span class="c1"></span> <span class="nf">Less</span><span class="p">(</span><span class="nx">i</span><span class="p">,</span> <span class="nx">j</span> <span class="kt">int</span><span class="p">)</span> <span class="kt">bool</span>
</span></span><span class="line"><span class="cl"> <span class="c1">// Swap swaps the elements with indexes i and j.
</span></span></span><span class="line"><span class="cl"><span class="c1"></span> <span class="nf">Swap</span><span class="p">(</span><span class="nx">i</span><span class="p">,</span> <span class="nx">j</span> <span class="kt">int</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span></code></pre></div><h2>オブジェクトのソート</h2>
<p>つまり,この <a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a><code>.Interface</code> インタフェースを持つ型であれば <a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a><code>.Sort()</code> 関数でソート可能ということになる。
たとえば以下のオブジェクト集合を考える。</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-go" data-lang="go"><span class="line"><span class="cl"><span class="c1">// A Planet defines the properties of a solar system object.
</span></span></span><span class="line"><span class="cl"><span class="c1"></span><span class="kd">type</span> <span class="nx">Planet</span> <span class="kd">struct</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">Name</span> <span class="kt">string</span>
</span></span><span class="line"><span class="cl"> <span class="nx">Mass</span> <span class="kt">float64</span>
</span></span><span class="line"><span class="cl"> <span class="nx">Distance</span> <span class="kt">float64</span>
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="kd">var</span> <span class="nx">planets</span> <span class="p">=</span> <span class="p">[]</span><span class="nx">Planet</span><span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="p">{</span><span class="s">"Mercury"</span><span class="p">,</span> <span class="mf">0.055</span><span class="p">,</span> <span class="mf">0.4</span><span class="p">},</span>
</span></span><span class="line"><span class="cl"> <span class="p">{</span><span class="s">"Venus"</span><span class="p">,</span> <span class="mf">0.815</span><span class="p">,</span> <span class="mf">0.7</span><span class="p">},</span>
</span></span><span class="line"><span class="cl"> <span class="p">{</span><span class="s">"Earth"</span><span class="p">,</span> <span class="mf">1.0</span><span class="p">,</span> <span class="mf">1.0</span><span class="p">},</span>
</span></span><span class="line"><span class="cl"> <span class="p">{</span><span class="s">"Mars"</span><span class="p">,</span> <span class="mf">0.107</span><span class="p">,</span> <span class="mf">1.5</span><span class="p">},</span>
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span></code></pre></div><p><code>Planet</code> オブジェクトの集合に対する <a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a><code>.Interface</code> インタフェースはこんな感じにする<sup id="fnref:1"><a href="#fn:1" class="footnote-ref" role="doc-noteref">1</a></sup>。</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-go" data-lang="go"><span class="line"><span class="cl"><span class="c1">// ByMass implements sort.Interface for []Planet based on the Mass field.
</span></span></span><span class="line"><span class="cl"><span class="c1"></span><span class="kd">type</span> <span class="nx">ByMass</span> <span class="p">[]</span><span class="nx">Planet</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="kd">func</span> <span class="p">(</span><span class="nx">a</span> <span class="nx">ByMass</span><span class="p">)</span> <span class="nf">Len</span><span class="p">()</span> <span class="kt">int</span> <span class="p">{</span> <span class="k">return</span> <span class="nb">len</span><span class="p">(</span><span class="nx">a</span><span class="p">)</span> <span class="p">}</span>
</span></span><span class="line"><span class="cl"><span class="kd">func</span> <span class="p">(</span><span class="nx">a</span> <span class="nx">ByMass</span><span class="p">)</span> <span class="nf">Less</span><span class="p">(</span><span class="nx">i</span><span class="p">,</span> <span class="nx">j</span> <span class="kt">int</span><span class="p">)</span> <span class="kt">bool</span> <span class="p">{</span> <span class="k">return</span> <span class="nx">a</span><span class="p">[</span><span class="nx">i</span><span class="p">].</span><span class="nx">Mass</span> <span class="p"><</span> <span class="nx">a</span><span class="p">[</span><span class="nx">j</span><span class="p">].</span><span class="nx">Mass</span> <span class="p">}</span>
</span></span><span class="line"><span class="cl"><span class="kd">func</span> <span class="p">(</span><span class="nx">a</span> <span class="nx">ByMass</span><span class="p">)</span> <span class="nf">Swap</span><span class="p">(</span><span class="nx">i</span><span class="p">,</span> <span class="nx">j</span> <span class="kt">int</span><span class="p">)</span> <span class="p">{</span> <span class="nx">a</span><span class="p">[</span><span class="nx">i</span><span class="p">],</span> <span class="nx">a</span><span class="p">[</span><span class="nx">j</span><span class="p">]</span> <span class="p">=</span> <span class="nx">a</span><span class="p">[</span><span class="nx">j</span><span class="p">],</span> <span class="nx">a</span><span class="p">[</span><span class="nx">i</span><span class="p">]</span> <span class="p">}</span>
</span></span></code></pre></div><p>つまり <code>Mass</code> フィールド値の昇順に並べるわけだ。</p>
<p>全体ではこんな感じになるだろう。</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-go" data-lang="go"><span class="line"><span class="cl"><span class="kn">package</span> <span class="nx">main</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="kn">import</span> <span class="p">(</span>
</span></span><span class="line"><span class="cl"> <span class="s">"fmt"</span>
</span></span><span class="line"><span class="cl"> <span class="s">"sort"</span>
</span></span><span class="line"><span class="cl"><span class="p">)</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="c1">// A Planet defines the properties of a solar system object.
</span></span></span><span class="line"><span class="cl"><span class="c1"></span><span class="kd">type</span> <span class="nx">Planet</span> <span class="kd">struct</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">Name</span> <span class="kt">string</span>
</span></span><span class="line"><span class="cl"> <span class="nx">Mass</span> <span class="kt">float64</span>
</span></span><span class="line"><span class="cl"> <span class="nx">Distance</span> <span class="kt">float64</span>
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="kd">func</span> <span class="p">(</span><span class="nx">p</span> <span class="nx">Planet</span><span class="p">)</span> <span class="nf">String</span><span class="p">()</span> <span class="kt">string</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="k">return</span> <span class="nx">p</span><span class="p">.</span><span class="nx">Name</span>
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="c1">// ByMass implements sort.Interface for []Planet based on the Mass field.
</span></span></span><span class="line"><span class="cl"><span class="c1"></span><span class="kd">type</span> <span class="nx">ByMass</span> <span class="p">[]</span><span class="nx">Planet</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="kd">func</span> <span class="p">(</span><span class="nx">a</span> <span class="nx">ByMass</span><span class="p">)</span> <span class="nf">Len</span><span class="p">()</span> <span class="kt">int</span> <span class="p">{</span> <span class="k">return</span> <span class="nb">len</span><span class="p">(</span><span class="nx">a</span><span class="p">)</span> <span class="p">}</span>
</span></span><span class="line"><span class="cl"><span class="kd">func</span> <span class="p">(</span><span class="nx">a</span> <span class="nx">ByMass</span><span class="p">)</span> <span class="nf">Less</span><span class="p">(</span><span class="nx">i</span><span class="p">,</span> <span class="nx">j</span> <span class="kt">int</span><span class="p">)</span> <span class="kt">bool</span> <span class="p">{</span> <span class="k">return</span> <span class="nx">a</span><span class="p">[</span><span class="nx">i</span><span class="p">].</span><span class="nx">Mass</span> <span class="p"><</span> <span class="nx">a</span><span class="p">[</span><span class="nx">j</span><span class="p">].</span><span class="nx">Mass</span> <span class="p">}</span>
</span></span><span class="line"><span class="cl"><span class="kd">func</span> <span class="p">(</span><span class="nx">a</span> <span class="nx">ByMass</span><span class="p">)</span> <span class="nf">Swap</span><span class="p">(</span><span class="nx">i</span><span class="p">,</span> <span class="nx">j</span> <span class="kt">int</span><span class="p">)</span> <span class="p">{</span> <span class="nx">a</span><span class="p">[</span><span class="nx">i</span><span class="p">],</span> <span class="nx">a</span><span class="p">[</span><span class="nx">j</span><span class="p">]</span> <span class="p">=</span> <span class="nx">a</span><span class="p">[</span><span class="nx">j</span><span class="p">],</span> <span class="nx">a</span><span class="p">[</span><span class="nx">i</span><span class="p">]</span> <span class="p">}</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="kd">func</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">planets</span> <span class="o">:=</span> <span class="p">[]</span><span class="nx">Planet</span><span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="p">{</span><span class="s">"Mercury"</span><span class="p">,</span> <span class="mf">0.055</span><span class="p">,</span> <span class="mf">0.4</span><span class="p">},</span>
</span></span><span class="line"><span class="cl"> <span class="p">{</span><span class="s">"Venus"</span><span class="p">,</span> <span class="mf">0.815</span><span class="p">,</span> <span class="mf">0.7</span><span class="p">},</span>
</span></span><span class="line"><span class="cl"> <span class="p">{</span><span class="s">"Earth"</span><span class="p">,</span> <span class="mf">1.0</span><span class="p">,</span> <span class="mf">1.0</span><span class="p">},</span>
</span></span><span class="line"><span class="cl"> <span class="p">{</span><span class="s">"Mars"</span><span class="p">,</span> <span class="mf">0.107</span><span class="p">,</span> <span class="mf">1.5</span><span class="p">},</span>
</span></span><span class="line"><span class="cl"> <span class="p">}</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"> <span class="k">for</span> <span class="nx">_</span><span class="p">,</span> <span class="nx">p</span> <span class="o">:=</span> <span class="k">range</span> <span class="nx">planets</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">fmt</span><span class="p">.</span><span class="nf">Printf</span><span class="p">(</span><span class="s">"%v "</span><span class="p">,</span> <span class="nx">p</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"> <span class="p">}</span>
</span></span><span class="line"><span class="cl"> <span class="nx">fmt</span><span class="p">.</span><span class="nf">Print</span><span class="p">(</span><span class="s">"\n"</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"> <span class="nx">sort</span><span class="p">.</span><span class="nf">Sort</span><span class="p">(</span><span class="nf">ByMass</span><span class="p">(</span><span class="nx">planets</span><span class="p">))</span>
</span></span><span class="line"><span class="cl"> <span class="k">for</span> <span class="nx">_</span><span class="p">,</span> <span class="nx">p</span> <span class="o">:=</span> <span class="k">range</span> <span class="nx">planets</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">fmt</span><span class="p">.</span><span class="nf">Printf</span><span class="p">(</span><span class="s">"%v "</span><span class="p">,</span> <span class="nx">p</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"> <span class="p">}</span>
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span></code></pre></div><p>結果は以下の通りで意図通りの動作になっているのが分かるだろう。</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-text" data-lang="text"><span class="line"><span class="cl">$ go run sort3.go
</span></span><span class="line"><span class="cl">Mercury Venus Earth Mars
</span></span><span class="line"><span class="cl">Mercury Mars Venus Earth
</span></span></code></pre></div><h2><code>sort.Slice()</code> 関数を使う場合</h2>
<p><a href="https://go.dev/ref/spec#Slice_types">slice</a> 限定であるが, <a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a><code>.Slice()</code> 関数を使えば <a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a><code>.Interface</code> インタフェースを定義しなくてもソートを行うことができる。
<a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a><code>.Slice()</code> 関数の定義は以下の通り。</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-go" data-lang="go"><span class="line"><span class="cl"><span class="kd">func</span> <span class="nf">Slice</span><span class="p">(</span><span class="nx">slice</span> <span class="kd">interface</span><span class="p">{},</span> <span class="nx">less</span> <span class="kd">func</span><span class="p">(</span><span class="nx">i</span><span class="p">,</span> <span class="nx">j</span> <span class="kt">int</span><span class="p">)</span> <span class="kt">bool</span><span class="p">)</span>
</span></span></code></pre></div><p>実際のコードはこんな感じになる。</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-go" data-lang="go"><span class="line"><span class="cl"><span class="kn">package</span> <span class="nx">main</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="kn">import</span> <span class="p">(</span>
</span></span><span class="line"><span class="cl"> <span class="s">"fmt"</span>
</span></span><span class="line"><span class="cl"> <span class="s">"sort"</span>
</span></span><span class="line"><span class="cl"><span class="p">)</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="c1">// A Planet defines the properties of a solar system object.
</span></span></span><span class="line"><span class="cl"><span class="c1"></span><span class="kd">type</span> <span class="nx">Planet</span> <span class="kd">struct</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">Name</span> <span class="kt">string</span>
</span></span><span class="line"><span class="cl"> <span class="nx">Mass</span> <span class="kt">float64</span>
</span></span><span class="line"><span class="cl"> <span class="nx">Distance</span> <span class="kt">float64</span>
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="kd">func</span> <span class="p">(</span><span class="nx">p</span> <span class="nx">Planet</span><span class="p">)</span> <span class="nf">String</span><span class="p">()</span> <span class="kt">string</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="k">return</span> <span class="nx">p</span><span class="p">.</span><span class="nx">Name</span>
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="kd">func</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">planets</span> <span class="o">:=</span> <span class="p">[]</span><span class="nx">Planet</span><span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="p">{</span><span class="s">"Mercury"</span><span class="p">,</span> <span class="mf">0.055</span><span class="p">,</span> <span class="mf">0.4</span><span class="p">},</span>
</span></span><span class="line"><span class="cl"> <span class="p">{</span><span class="s">"Venus"</span><span class="p">,</span> <span class="mf">0.815</span><span class="p">,</span> <span class="mf">0.7</span><span class="p">},</span>
</span></span><span class="line"><span class="cl"> <span class="p">{</span><span class="s">"Earth"</span><span class="p">,</span> <span class="mf">1.0</span><span class="p">,</span> <span class="mf">1.0</span><span class="p">},</span>
</span></span><span class="line"><span class="cl"> <span class="p">{</span><span class="s">"Mars"</span><span class="p">,</span> <span class="mf">0.107</span><span class="p">,</span> <span class="mf">1.5</span><span class="p">},</span>
</span></span><span class="line"><span class="cl"> <span class="p">}</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"> <span class="k">for</span> <span class="nx">_</span><span class="p">,</span> <span class="nx">p</span> <span class="o">:=</span> <span class="k">range</span> <span class="nx">planets</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">fmt</span><span class="p">.</span><span class="nf">Printf</span><span class="p">(</span><span class="s">"%v "</span><span class="p">,</span> <span class="nx">p</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"> <span class="p">}</span>
</span></span><span class="line"><span class="cl"> <span class="nx">fmt</span><span class="p">.</span><span class="nf">Print</span><span class="p">(</span><span class="s">"\n"</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"> <span class="nx">sort</span><span class="p">.</span><span class="nf">Slice</span><span class="p">(</span><span class="nx">planets</span><span class="p">,</span> <span class="kd">func</span><span class="p">(</span><span class="nx">i</span><span class="p">,</span> <span class="nx">j</span> <span class="kt">int</span><span class="p">)</span> <span class="kt">bool</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="k">return</span> <span class="nx">planets</span><span class="p">[</span><span class="nx">i</span><span class="p">].</span><span class="nx">Mass</span> <span class="p"><</span> <span class="nx">planets</span><span class="p">[</span><span class="nx">j</span><span class="p">].</span><span class="nx">Mass</span>
</span></span><span class="line"><span class="cl"> <span class="p">})</span>
</span></span><span class="line"><span class="cl"> <span class="k">for</span> <span class="nx">_</span><span class="p">,</span> <span class="nx">p</span> <span class="o">:=</span> <span class="k">range</span> <span class="nx">planets</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">fmt</span><span class="p">.</span><span class="nf">Printf</span><span class="p">(</span><span class="s">"%v "</span><span class="p">,</span> <span class="nx">p</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"> <span class="p">}</span>
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span></code></pre></div><p><a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a><code>.Slice()</code> 関数の第2引数が関数閉包(closure)になっている点に注意<sup id="fnref:2"><a href="#fn:2" class="footnote-ref" role="doc-noteref">2</a></sup>。
これなら第2引数の関数の内容を変えれば任意の規則でソートを行うことができる。</p>
<p>結果は <a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a><code>.Interface</code> インタフェースがある場合と同じく</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-text" data-lang="text"><span class="line"><span class="cl">$ go run sort4.go
</span></span><span class="line"><span class="cl">Mercury Venus Earth Mars
</span></span><span class="line"><span class="cl">Mercury Mars Venus Earth
</span></span></code></pre></div><p>となった。</p>
<p>さて,実際に <a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a><code>.Slice()</code> 関数を覗いてみよう。</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-go" data-lang="go"><span class="line"><span class="cl"><span class="c1">// maxDepth returns a threshold at which quicksort should switch
</span></span></span><span class="line"><span class="cl"><span class="c1">// to heapsort. It returns 2*ceil(lg(n+1)).
</span></span></span><span class="line"><span class="cl"><span class="c1"></span><span class="kd">func</span> <span class="nf">maxDepth</span><span class="p">(</span><span class="nx">n</span> <span class="kt">int</span><span class="p">)</span> <span class="kt">int</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="kd">var</span> <span class="nx">depth</span> <span class="kt">int</span>
</span></span><span class="line"><span class="cl"> <span class="k">for</span> <span class="nx">i</span> <span class="o">:=</span> <span class="nx">n</span><span class="p">;</span> <span class="nx">i</span> <span class="p">></span> <span class="mi">0</span><span class="p">;</span> <span class="nx">i</span> <span class="o">>>=</span> <span class="mi">1</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">depth</span><span class="o">++</span>
</span></span><span class="line"><span class="cl"> <span class="p">}</span>
</span></span><span class="line"><span class="cl"> <span class="k">return</span> <span class="nx">depth</span> <span class="o">*</span> <span class="mi">2</span>
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="c1">// lessSwap is a pair of Less and Swap function for use with the
</span></span></span><span class="line"><span class="cl"><span class="c1">// auto-generated func-optimized variant of sort.go in
</span></span></span><span class="line"><span class="cl"><span class="c1">// zfuncversion.go.
</span></span></span><span class="line"><span class="cl"><span class="c1"></span><span class="kd">type</span> <span class="nx">lessSwap</span> <span class="kd">struct</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">Less</span> <span class="kd">func</span><span class="p">(</span><span class="nx">i</span><span class="p">,</span> <span class="nx">j</span> <span class="kt">int</span><span class="p">)</span> <span class="kt">bool</span>
</span></span><span class="line"><span class="cl"> <span class="nx">Swap</span> <span class="kd">func</span><span class="p">(</span><span class="nx">i</span><span class="p">,</span> <span class="nx">j</span> <span class="kt">int</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="c1">// Slice sorts the provided slice given the provided less function.
</span></span></span><span class="line"><span class="cl"><span class="c1">//
</span></span></span><span class="line"><span class="cl"><span class="c1">// The sort is not guaranteed to be stable. For a stable sort, use
</span></span></span><span class="line"><span class="cl"><span class="c1">// SliceStable.
</span></span></span><span class="line"><span class="cl"><span class="c1">//
</span></span></span><span class="line"><span class="cl"><span class="c1">// The function panics if the provided interface is not a slice.
</span></span></span><span class="line"><span class="cl"><span class="c1"></span><span class="kd">func</span> <span class="nf">Slice</span><span class="p">(</span><span class="nx">slice</span> <span class="kd">interface</span><span class="p">{},</span> <span class="nx">less</span> <span class="kd">func</span><span class="p">(</span><span class="nx">i</span><span class="p">,</span> <span class="nx">j</span> <span class="kt">int</span><span class="p">)</span> <span class="kt">bool</span><span class="p">)</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">rv</span> <span class="o">:=</span> <span class="nx">reflect</span><span class="p">.</span><span class="nf">ValueOf</span><span class="p">(</span><span class="nx">slice</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"> <span class="nx">swap</span> <span class="o">:=</span> <span class="nx">reflect</span><span class="p">.</span><span class="nf">Swapper</span><span class="p">(</span><span class="nx">slice</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"> <span class="nx">length</span> <span class="o">:=</span> <span class="nx">rv</span><span class="p">.</span><span class="nf">Len</span><span class="p">()</span>
</span></span><span class="line"><span class="cl"> <span class="nf">quickSort_func</span><span class="p">(</span><span class="nx">lessSwap</span><span class="p">{</span><span class="nx">less</span><span class="p">,</span> <span class="nx">swap</span><span class="p">},</span> <span class="mi">0</span><span class="p">,</span> <span class="nx">length</span><span class="p">,</span> <span class="nf">maxDepth</span><span class="p">(</span><span class="nx">length</span><span class="p">))</span>
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span></code></pre></div><p><a href="https://pkg.go.dev/reflect/" title="reflect - The Go Programming Language"><code>reflect</code></a><code>.ValueOf()</code> 関数は <a href="https://pkg.go.dev/reflect/" title="reflect - The Go Programming Language"><code>reflect</code></a><code>.Value</code> を取得する関数だ<sup id="fnref:3"><a href="#fn:3" class="footnote-ref" role="doc-noteref">3</a></sup>。
その次の <a href="https://pkg.go.dev/reflect/" title="reflect - The Go Programming Language"><code>reflect</code></a><code>.Swapper()</code> 関数がポイント。
この関数は先程の <a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a><code>.Interface</code> インタフェースでいうところの <code>Swap()</code> 関数に相当するものを返す<sup id="fnref:4"><a href="#fn:4" class="footnote-ref" role="doc-noteref">4</a></sup>。
なのでこんなこともできる。</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-go" data-lang="go"><span class="line"><span class="cl"><span class="kn">package</span> <span class="nx">main</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="kn">import</span> <span class="p">(</span>
</span></span><span class="line"><span class="cl"> <span class="s">"fmt"</span>
</span></span><span class="line"><span class="cl"> <span class="s">"reflect"</span>
</span></span><span class="line"><span class="cl"><span class="p">)</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="kd">func</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">s</span> <span class="o">:=</span> <span class="p">[]</span><span class="kt">int</span><span class="p">{</span><span class="mi">1</span><span class="p">,</span> <span class="mi">2</span><span class="p">,</span> <span class="mi">3</span><span class="p">}</span>
</span></span><span class="line"><span class="cl"> <span class="nx">fmt</span><span class="p">.</span><span class="nf">Println</span><span class="p">(</span><span class="nx">s</span><span class="p">)</span> <span class="c1">// [1 2 3]
</span></span></span><span class="line"><span class="cl"><span class="c1"></span> <span class="nx">reflect</span><span class="p">.</span><span class="nf">Swapper</span><span class="p">(</span><span class="nx">s</span><span class="p">)(</span><span class="mi">0</span><span class="p">,</span> <span class="mi">2</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"> <span class="nx">fmt</span><span class="p">.</span><span class="nf">Println</span><span class="p">(</span><span class="nx">s</span><span class="p">)</span> <span class="c1">// [3 2 1]
</span></span></span><span class="line"><span class="cl"><span class="c1"></span><span class="p">}</span>
</span></span></code></pre></div><p>残りの <code>Len()</code> 関数に相当するものは <a href="https://pkg.go.dev/reflect/" title="reflect - The Go Programming Language"><code>reflect</code></a><code>.Value</code> で用意されているし, <code>Less()</code> 関数に相当するものは <a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a><code>.Slice()</code> 関数の引数として与えられる。
これでソートに必要な3つの関数が揃うわけだ。</p>
<p>ちなみに <code>quickSort_func()</code> 関数は,名前の通り,クイックソートである。
ただしクイックソートでは安定ソートにならないため,安定ソートを実行するための <a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a><code>.SliceStable()</code> 関数も用意されている。
<a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a><code>.SliceStable()</code> 関数ではアルゴリズムに挿入ソートを用いる<sup id="fnref:5"><a href="#fn:5" class="footnote-ref" role="doc-noteref">5</a></sup>。</p>
<h2>【2023-08-10 追記】 slices 標準パッケージを使う</h2>
<p><a href="https://go.dev/" title="The Go Programming Language">Go</a> 1.21 から <a href="https://pkg.go.dev/slices" title="slices package - slices - Go Packages"><code>slices</code></a> 標準パッケージが追加された。
このパッケージにも <a href="https://go.dev/ref/spec#Slice_types">slice</a> をソートする関数が定義されている。</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-go" data-lang="go"><span class="line"><span class="cl"><span class="c1">// Sort sorts a slice of any ordered type in ascending order.
</span></span></span><span class="line"><span class="cl"><span class="c1">// When sorting floating-point numbers, NaNs are ordered before other values.
</span></span></span><span class="line"><span class="cl"><span class="c1"></span><span class="kd">func</span> <span class="nx">Sort</span><span class="p">[</span><span class="nx">S</span> <span class="p">~[]</span><span class="nx">E</span><span class="p">,</span> <span class="nx">E</span> <span class="nx">cmp</span><span class="p">.</span><span class="nx">Ordered</span><span class="p">](</span><span class="nx">x</span> <span class="nx">S</span><span class="p">)</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">n</span> <span class="o">:=</span> <span class="nb">len</span><span class="p">(</span><span class="nx">x</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"> <span class="nf">pdqsortOrdered</span><span class="p">(</span><span class="nx">x</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="nx">n</span><span class="p">,</span> <span class="nx">bits</span><span class="p">.</span><span class="nf">Len</span><span class="p">(</span><span class="nb">uint</span><span class="p">(</span><span class="nx">n</span><span class="p">)))</span>
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="c1">// SortFunc sorts the slice x in ascending order as determined by the cmp
</span></span></span><span class="line"><span class="cl"><span class="c1">// function. This sort is not guaranteed to be stable.
</span></span></span><span class="line"><span class="cl"><span class="c1">// cmp(a, b) should return a negative number when a < b, a positive number when
</span></span></span><span class="line"><span class="cl"><span class="c1">// a > b and zero when a == b.
</span></span></span><span class="line"><span class="cl"><span class="c1">//
</span></span></span><span class="line"><span class="cl"><span class="c1">// SortFunc requires that cmp is a strict weak ordering.
</span></span></span><span class="line"><span class="cl"><span class="c1">// See https://en.wikipedia.org/wiki/Weak_ordering#Strict_weak_orderings.
</span></span></span><span class="line"><span class="cl"><span class="c1"></span><span class="kd">func</span> <span class="nx">SortFunc</span><span class="p">[</span><span class="nx">S</span> <span class="p">~[]</span><span class="nx">E</span><span class="p">,</span> <span class="nx">E</span> <span class="nx">any</span><span class="p">](</span><span class="nx">x</span> <span class="nx">S</span><span class="p">,</span> <span class="nx">cmp</span> <span class="kd">func</span><span class="p">(</span><span class="nx">a</span><span class="p">,</span> <span class="nx">b</span> <span class="nx">E</span><span class="p">)</span> <span class="kt">int</span><span class="p">)</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">n</span> <span class="o">:=</span> <span class="nb">len</span><span class="p">(</span><span class="nx">x</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"> <span class="nf">pdqsortCmpFunc</span><span class="p">(</span><span class="nx">x</span><span class="p">,</span> <span class="mi">0</span><span class="p">,</span> <span class="nx">n</span><span class="p">,</span> <span class="nx">bits</span><span class="p">.</span><span class="nf">Len</span><span class="p">(</span><span class="nb">uint</span><span class="p">(</span><span class="nx">n</span><span class="p">)),</span> <span class="nx">cmp</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="c1">// SortStableFunc sorts the slice x while keeping the original order of equal
</span></span></span><span class="line"><span class="cl"><span class="c1">// elements, using cmp to compare elements in the same way as [SortFunc].
</span></span></span><span class="line"><span class="cl"><span class="c1"></span><span class="kd">func</span> <span class="nx">SortStableFunc</span><span class="p">[</span><span class="nx">S</span> <span class="p">~[]</span><span class="nx">E</span><span class="p">,</span> <span class="nx">E</span> <span class="nx">any</span><span class="p">](</span><span class="nx">x</span> <span class="nx">S</span><span class="p">,</span> <span class="nx">cmp</span> <span class="kd">func</span><span class="p">(</span><span class="nx">a</span><span class="p">,</span> <span class="nx">b</span> <span class="nx">E</span><span class="p">)</span> <span class="kt">int</span><span class="p">)</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nf">stableCmpFunc</span><span class="p">(</span><span class="nx">x</span><span class="p">,</span> <span class="nb">len</span><span class="p">(</span><span class="nx">x</span><span class="p">),</span> <span class="nx">cmp</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span></code></pre></div><p>安定ソートは <a href="https://pkg.go.dev/slices" title="slices package - slices - Go Packages"><code>slices</code></a><code>.SortStableFunc()</code> 関数のみか。
ソートのアルゴリズムについては割愛するが,コメントには “<code>pattern-defeating quicksort(pdqsort)</code>” と書かれている。</p>
<p>さて,これらの関数を使えば前節のコードを</p>
<div class="highlight"><pre tabindex="0" class="chroma"><code class="language-go" data-lang="go"><span class="line"><span class="cl"><span class="kn">package</span> <span class="nx">main</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="kn">import</span> <span class="p">(</span>
</span></span><span class="line hl"><span class="cl"> <span class="s">"cmp"</span>
</span></span><span class="line"><span class="cl"> <span class="s">"fmt"</span>
</span></span><span class="line hl"><span class="cl"> <span class="s">"slices"</span>
</span></span><span class="line"><span class="cl"><span class="p">)</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="c1">// A Planet defines the properties of a solar system object.
</span></span></span><span class="line"><span class="cl"><span class="c1"></span><span class="kd">type</span> <span class="nx">Planet</span> <span class="kd">struct</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">Name</span> <span class="kt">string</span>
</span></span><span class="line"><span class="cl"> <span class="nx">Mass</span> <span class="kt">float64</span>
</span></span><span class="line"><span class="cl"> <span class="nx">Distance</span> <span class="kt">float64</span>
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="kd">func</span> <span class="p">(</span><span class="nx">p</span> <span class="nx">Planet</span><span class="p">)</span> <span class="nf">String</span><span class="p">()</span> <span class="kt">string</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="k">return</span> <span class="nx">p</span><span class="p">.</span><span class="nx">Name</span>
</span></span><span class="line"><span class="cl"><span class="p">}</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"><span class="kd">func</span> <span class="nf">main</span><span class="p">()</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">planets</span> <span class="o">:=</span> <span class="p">[]</span><span class="nx">Planet</span><span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="p">{</span><span class="s">"Mercury"</span><span class="p">,</span> <span class="mf">0.055</span><span class="p">,</span> <span class="mf">0.4</span><span class="p">},</span>
</span></span><span class="line"><span class="cl"> <span class="p">{</span><span class="s">"Venus"</span><span class="p">,</span> <span class="mf">0.815</span><span class="p">,</span> <span class="mf">0.7</span><span class="p">},</span>
</span></span><span class="line"><span class="cl"> <span class="p">{</span><span class="s">"Earth"</span><span class="p">,</span> <span class="mf">1.0</span><span class="p">,</span> <span class="mf">1.0</span><span class="p">},</span>
</span></span><span class="line"><span class="cl"> <span class="p">{</span><span class="s">"Mars"</span><span class="p">,</span> <span class="mf">0.107</span><span class="p">,</span> <span class="mf">1.5</span><span class="p">},</span>
</span></span><span class="line"><span class="cl"> <span class="p">}</span>
</span></span><span class="line"><span class="cl">
</span></span><span class="line"><span class="cl"> <span class="k">for</span> <span class="nx">_</span><span class="p">,</span> <span class="nx">p</span> <span class="o">:=</span> <span class="k">range</span> <span class="nx">planets</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">fmt</span><span class="p">.</span><span class="nf">Printf</span><span class="p">(</span><span class="s">"%v "</span><span class="p">,</span> <span class="nx">p</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"> <span class="p">}</span>
</span></span><span class="line"><span class="cl"> <span class="nx">fmt</span><span class="p">.</span><span class="nf">Print</span><span class="p">(</span><span class="s">"\n"</span><span class="p">)</span>
</span></span><span class="line hl"><span class="cl"> <span class="nx">slices</span><span class="p">.</span><span class="nf">SortFunc</span><span class="p">(</span><span class="nx">planets</span><span class="p">,</span> <span class="kd">func</span><span class="p">(</span><span class="nx">pl</span><span class="p">,</span> <span class="nx">pr</span> <span class="nx">Planet</span><span class="p">)</span> <span class="kt">int</span> <span class="p">{</span>
</span></span><span class="line hl"><span class="cl"> <span class="k">return</span> <span class="nx">cmp</span><span class="p">.</span><span class="nf">Compare</span><span class="p">(</span><span class="nx">pl</span><span class="p">.</span><span class="nx">Mass</span><span class="p">,</span> <span class="nx">pr</span><span class="p">.</span><span class="nx">Mass</span><span class="p">)</span>
</span></span><span class="line hl"><span class="cl"> <span class="p">})</span>
</span></span><span class="line"><span class="cl"> <span class="k">for</span> <span class="nx">_</span><span class="p">,</span> <span class="nx">p</span> <span class="o">:=</span> <span class="k">range</span> <span class="nx">planets</span> <span class="p">{</span>
</span></span><span class="line"><span class="cl"> <span class="nx">fmt</span><span class="p">.</span><span class="nf">Printf</span><span class="p">(</span><span class="s">"%v "</span><span class="p">,</span> <span class="nx">p</span><span class="p">)</span>
</span></span><span class="line"><span class="cl"> <span class="p">}</span>
</span></span><span class="line"><span class="cl"> <span class="c1">// Output:
</span></span></span><span class="line"><span class="cl"><span class="c1"></span> <span class="c1">// Mercury Venus Earth Mars
</span></span></span><span class="line"><span class="cl"><span class="c1"></span> <span class="c1">// Mercury Mars Venus Earth
</span></span></span><span class="line"><span class="cl"><span class="c1"></span><span class="p">}</span>
</span></span></code></pre></div><p>てな感じに書き換えることができる。</p>
<p><a href="https://pkg.go.dev/cmp" title="cmp package - cmp - Go Packages"><code>cmp</code></a> パッケージも <a href="https://go.dev/" title="The Go Programming Language">Go</a> 1.21 で追加されたものだ。
<a href="https://pkg.go.dev/slices" title="slices package - slices - Go Packages"><code>slices</code></a> と同じく Generics を使って比較に関する型と関数を定義している。</p>
<h2>ブックマーク</h2>
<ul>
<li><a href="http://qiita.com/sugyan/items/fd7138a756c1a409f5fd">sliceのシャッフル - Qiita</a> : <a href="https://en.wikipedia.org/wiki/Fisher%E2%80%93Yates_shuffle">Fisher–Yates shuffle</a> というアルゴリズムらしい</li>
<li><a href="http://qiita.com/nyamadandan/items/2c82011801b148c98e52">Go言語でバイトニックソート実装してみた - Qiita</a></li>
<li><a href="http://qiita.com/ohkawa/items/269507985b3ae10cbff9">Goでバケットソートアルゴリズム(ビット列を使用) - Qiita</a></li>
<li><a href="http://qiita.com/amesho/items/64dcd231038c96345848">Goでのアルゴリズムクイックリファレンス第2版(4.1.1 挿入ソート) - Qiita</a></li>
<li><a href="http://qiita.com/tchssk/items/b61f1f06d22a6232d4c8">interface{} をソートする - Qiita</a></li>
<li><a href="http://mattn.kaoriya.net/software/lang/go/20161004092237.htm">Big Sky :: golang の sort インタフェース難しい問題が解決した</a></li>
<li><a href="https://text.baldanders.info/remark/2017/02/go-1_8-released/">Go 言語 1.8 がリリース</a> : <a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a><code>.Slice()</code> 関数はバージョン 1.8 で導入された</li>
<li><a href="https://qiita.com/chimatter/items/f908507287fe2c7030e9">sort.Slice に学ぶ高速化のヒント - Qiita</a>
<ul>
<li><a href="https://qiita.com/chimatter/items/bc8f3ab3e617211b9a24">sort.Sort と sort.Slice の速度比較 - Qiita</a></li>
</ul>
</li>
<li><a href="http://zenito9970.hatenablog.com/entry/2015/05/30/155726">golang でクイックソートを並列化してみる - 長文書くところ</a></li>
<li><a href="https://qiita.com/drken/items/44c60118ab3703f7727f">「ソート」を極める! 〜 なぜソートを学ぶのか 〜 - Qiita</a> : ソート・アルゴリズムの概説。よくまとまっている</li>
<li><a href="https://qiita.com/karaimonoOitii/items/d9dfd8b9d3708ca947d9">Goでスターリンソート - Qiita</a> : (笑)</li>
<li><a href="http://kazoo04.hatenablog.com/entry/2012/12/10/183847">Quicksort の攻撃方法 - Sideswipe</a></li>
</ul>
<h2>参考図書</h2>
<div class="hreview">
<div class="photo"><a href="https://www.amazon.co.jp/dp/B099928SJD?tag=baldandersinf-22&linkCode=ogi&th=1&psc=1"><img src="https://m.media-amazon.com/images/I/416Stewy0NS._SL160_.jpg" width="123" alt="photo"></a></div>
<dl>
<dt class="item"><a class="fn url" href="https://www.amazon.co.jp/dp/B099928SJD?tag=baldandersinf-22&linkCode=ogi&th=1&psc=1">プログラミング言語Go</a></dt>
<dd>アラン・ドノバン (著), ブライアン・カーニハン (著), 柴田芳樹 (著)</dd>
<dd>丸善出版 2016-06-20 (Release 2021-07-13)</dd>
<dd>Kindle版</dd>
<dd>B099928SJD (ASIN)</dd>
<dd>評価<abbr class="rating fa-sm" title="5"> <i class="fas fa-star"></i> <i class="fas fa-star"></i> <i class="fas fa-star"></i> <i class="fas fa-star"></i> <i class="fas fa-star"></i></abbr></dd>
</dl>
<p class="description">Kindle 版出た! 一部内容が古びてしまったが,この本は Go 言語の教科書と言ってもいいだろう。感想は<a href="https://text.baldanders.info/remark/2016/07/go-programming-language/" >こちら</a>。</p>
<p class="powered-by">reviewed by <a href='#maker' class='reviewer'>Spiegel</a> on <abbr class="dtreviewed" title="2021-05-22">2021-05-22</abbr> (powered by <a href="https://affiliate.amazon.co.jp/assoc_credentials/home">PA-APIv5</a>)</p>
</div> <!-- プログラミング言語Go -->
<div class="hreview">
<div class="photo"><a href="https://www.amazon.co.jp/dp/B00I8AT1FO?tag=baldandersinf-22&linkCode=ogi&th=1&psc=1"><img src="https://m.media-amazon.com/images/I/41353H+BzFL._SL160_.jpg" width="113" alt="photo"></a></div>
<dl>
<dt class="item"><a class="fn url" href="https://www.amazon.co.jp/dp/B00I8AT1FO?tag=baldandersinf-22&linkCode=ogi&th=1&psc=1">数学ガール/乱択アルゴリズム</a></dt>
<dd>結城 浩 (著)</dd>
<dd>SBクリエイティブ 2011-02-25 (Release 2014-03-12)</dd>
<dd>Kindle版</dd>
<dd>B00I8AT1FO (ASIN)</dd>
<dd>評価<abbr class="rating fa-sm" title="5"> <i class="fas fa-star"></i> <i class="fas fa-star"></i> <i class="fas fa-star"></i> <i class="fas fa-star"></i> <i class="fas fa-star"></i></abbr></dd>
</dl>
<p class="description">工学ガール,リサちゃん登場!</p>
<p class="powered-by">reviewed by <a href='#maker' class='reviewer'>Spiegel</a> on <abbr class="dtreviewed" title="2015-04-19">2015-04-19</abbr> (powered by <a href="https://affiliate.amazon.co.jp/assoc_credentials/home">PA-APIv5</a>)</p>
</div> <!-- 数学ガール/乱択アルゴリズム -->
<div class="footnotes" role="doc-endnotes">
<hr>
<ol>
<li id="fn:1">
<p>今回は簡単のため <a href="https://go.dev/ref/spec#Slice_types">slice</a> を使っているが,データ集合は <a href="https://go.dev/ref/spec#Slice_types">slice</a> である必要はなく <a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a><code>.Interface</code> インタフェースを持つ任意のオブジェクトであればよい。 <a href="#fnref:1" class="footnote-backref" role="doc-backlink">↩︎</a></p>
</li>
<li id="fn:2">
<p>つか, <a href="https://go.dev/" title="The Go Programming Language">Go 言語</a>の関数は全て関数閉包として動作するんだけどね。 <a href="#fnref:2" class="footnote-backref" role="doc-backlink">↩︎</a></p>
</li>
<li id="fn:3">
<p><a href="https://pkg.go.dev/reflect/" title="reflect - The Go Programming Language"><code>reflect</code></a> パッケージについての詳細は割愛する。簡単に言うと, <a href="https://go.dev/" title="The Go Programming Language">Go 言語</a>において <a href="https://go.dev/doc/effective_go#interfaces_and_types" title="Effective Go - The Go Programming Language">interface</a> 型のインスタンスは型情報と値への参照の2つを保持していて,これに対応するのが <a href="https://pkg.go.dev/reflect/" title="reflect - The Go Programming Language"><code>reflect</code></a><code>.Type</code> と <a href="https://pkg.go.dev/reflect/" title="reflect - The Go Programming Language"><code>reflect</code></a><code>.Value</code> である(参考: <a href="https://research.swtch.com/interfaces">research!rsc: Go Data Structures: Interfaces</a>)。 <a href="#fnref:3" class="footnote-backref" role="doc-backlink">↩︎</a></p>
</li>
<li id="fn:4">
<p><a href="https://pkg.go.dev/reflect/" title="reflect - The Go Programming Language"><code>reflect</code></a><code>.Swapper()</code> 関数は引数の型が <a href="https://go.dev/ref/spec#Slice_types">slice</a> であることを前提にしていて, <a href="https://go.dev/ref/spec#Slice_types">slice</a> でない場合は panic が返る。 <a href="#fnref:4" class="footnote-backref" role="doc-backlink">↩︎</a></p>
</li>
<li id="fn:5">
<p><a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a><code>.Sort()</code> 関数も同じくクイックソートである。これの安定ソート版が <a href="https://pkg.go.dev/sort/" title="sort - The Go Programming Language"><code>sort</code></a><code>.Stable()</code> 関数で同じく挿入ソートを用いている。 <a href="#fnref:5" class="footnote-backref" role="doc-backlink">↩︎</a></p>
</li>
</ol>
</div>