P202で、共変、反変の説明をしている。これまでscalaの本やネットの情報を見ても、わかりずらいところだ。
EのサブクラスがEsub、スーパークラスをEsuperとして説明している。
「変数funcは、引数としてEを受け取ることを要求している。一方で、Eは、Esuperの派生型なので、Esuperとしてふるまうことは保証されています。(中略)一方で、EはEsubがどのようにEを拡張しているか知らないため、Esubとしてふるまうことができない。そのため、funcはEsub型を受け取ることができない。」
おもしろい説明の例がありました。こちらです。以下のその抜粋です。参考にさせていただきました。
猫を何かに変換する装置の一種として、動物を変換する装置が含まれるのは自然です。動物を変換する装置で猫を変換できるからです。
また、何かを動物に変換する装置の一種として、何かを人間に変換する装置が含まれるのは自然です。人間も動物の一種だからです。
集合式で書くと
動物 ⊇ 猫 → 動物を何かに変換する装置 ⊆ 猫を何かに変換する装置 (反変性)
人間 ⊆ 動物 → 何かを人間に変換する装置 ⊆ 何かを動物に変換する装置 (共変性)
・動物を何かに変換するのは、猫を変換する装置、犬を変換する装置、、等の共通(AND)集合なので、当然、猫を変換する装置よりも集合としては小さくなるということでしょうか。?
・あるものを人間に変換する装置、あるものを犬に変換する装置、、、等の和(OR)集合が、あるものを動物に変換する装置、、と考えれば、集合の包含関係は上記のようになる?
Wikipediaには、以下の説明がある
T 型の引数を持つ関数呼び出し (fun f (x : T) : Integer と定義) は、T ≤ S のとき、fun g(x: S) : Integer と定義される関数 g で置換可能である。言い換えると、g は、引数の型に関して f より寛容であり、f と同様に Integer を返すので、f をいつでも置換できる。このように、関数引数を許す言語においては、 g ≤ f と f の引数の型とは反変である。
0 件のコメント:
コメントを投稿