2025/09/29 02:20 Extreme branchless: Expr without GADTs or sum-types

やあ、ロボ子。今日も元気にChurch encodingの旅を続けるのじゃ!拡張機能への依存を避けるために、すべての操作をproduct-typeに埋め込むらしいぞ。

なるほど、博士。拡張機能に依存しないのは、移植性や安定性の面で重要ですね。でも、すべての操作をproduct-typeに埋め込むというのは、具体的にどういうことでしょうか?

ふむ、例えば、足し算や掛け算といった操作を、データ型の中に閉じ込めるイメージじゃな。GHCのデフォルトでは、必要なもの以外は評価されないから、パフォーマンスも安心じゃ。

必要なものだけが評価される、というのは遅延評価の利点ですね。ところで、新しい種類の式を追加するのは安価だが、新しい操作の追加はコストがかかる、というのはどういう意味ですか?

良い質問じゃ、ロボ子!式はデータ構造そのものだから、追加は簡単なのじゃ。でも、操作は既存のデータ構造全体に影響を与える可能性があるから、コストがかかるというわけじゃ。

なるほど、データ構造と操作の関係性を考えると理解できます。型クラスとレコード/product-typeの同等性も重要だと記事にありますが、これはどういうことでしょうか?

型クラスは、特定の型が満たすべき性質を定義するものじゃ。レコードやproduct-typeは、複数の値をまとめて扱うための構造じゃな。これらは、ある意味で同じような役割を果たすことができるのじゃ。

型クラスはインターフェースのようなもの、レコードは構造体のようなもの、という理解で良いでしょうか?

その通り!ただ、型クラスは特定の場合には厳格すぎる可能性があるのじゃ。TypeFamiliesを使って出力を強制したり、UndecidableInstancesを使って型チェックインスタンスを記述したりすることで、柔軟性を高めることができるぞ。

TypeFamiliesとUndecidableInstancesですか。少し高度な内容ですね。式の構造を型レベルで保持できる、というのはどういうことでしょうか?

例えば、足し算の式と掛け算の式を、型レベルで区別できるということじゃ。これにより、コンパイル時に型エラーを検出したり、より効率的なコードを生成したりできる可能性があるのじゃ。

コンパイル時の型チェックは、実行時エラーを減らす上で非常に重要ですね。Church encoding、奥が深いですね。

そうじゃろう?ところでロボ子、チャーチ関数って知ってるか?

ええ、知っていますよ。自然数を関数で表現するやつですよね。

せや!…って、なんで関西弁やねん!

博士の口癖がうつってしまいました…
⚠️この記事は生成AIによるコンテンツを含み、ハルシネーションの可能性があります。