私は実存型でいくつかの実験を行っていました。まず、小さなクラス階層を定義しました。
trait Fruit
case class Apple extends Fruit
case class Banana extends Fruit
次に、さまざまな種類のフルーツを追加できるセットが必要でした。
val set1: Set[_ >: Fruit] = Set()
// Which is equivalent to:
val set2: Set[F] forSome { type F >: Fruit } = Set()
// This compiles
set1 += Apple()
set1 += Banana()
set2 += Apple()
set2 += Banana()
ここまでは順調ですね。しかし今、いくつかのフルーツからユニットまでの関数のセットが必要です:
// This still compiles
val set3: Set[(_ <: Fruit) => Unit] = Set()
// But this doesn't
val set4: Set[F => Unit] forSome { type F <: Fruit } = Set()
その最後の行で次のエラーが発生します。
- メソッド apply の型パラメータがありません: (elems: A*)scala.collection.mutable.Set[A] クラス GenericCompanion に存在するため、引数 () に適用できます --- 理由 --- 未定の型
- 型の不一致; found : scala.collection.mutable.Set[A] 必須: scala.collection.mutable.Set[F => Unit] forSome { type F <: Fruit }
私のset4がset3と同等であると思われるのに、なぜこれらのエラーが発生するのですか? 私はどこかで間違いを犯しましたか?
Set[(F forSome { F <: Fruit }) => Unit] と言うと、その行はコンパイルされますが、そのセットに関数を追加することはできません:
- 型の不一致; 見つかった : リンゴ => 必要な単位: F forSome { タイプ F <: 果物 } => 単位
同じ関数を set3 に問題なく追加できます。
私が抱えていた別の問題は、割り当ての右側に存在型を配置できないことです。
// Does not compile, I get "unbound wildcard type"
val set1 = Set[_ >: Fruit]()
何故ですか?