次のコードでは、 の証拠がR[A]
ありB
、 のサブタイプであるため、のタイプを推測して証拠を使用するA
ことを期待します。しかし、scalac はそうすることを拒否します。foo
A
RA
trait R[T]
case class A(i: Int)
object A {
implicit object RA extends R[A]
}
class B(i: Int) extends A(i)
def foo[T](x : T)(implicit ev: R[T]) = 0
println(foo(new B(1))) // infers T as B and fails to find implicit R[B]
println(foo(new B(1) : A)) // Works, but undesirable
私はこれを試しました:
def foo[T, TT >: T](x : T)(implicit ev: R[TT]) = 0
しかし、それでもうまくいきません。
さて、私が定義すると:
def foo[T](x : T)(implicit ev: R[TT] forSome {type TT <: T}) = 0
推論は機能しますが、実際のコードでは TT を参照する必要があります。
編集: A の証拠を A コンパニオン オブジェクトに移動したので、この解決策はもう機能しないようです。現実的な設定では、証拠は常にコンパニオン オブジェクトにあり、暗黙の検索でそれを見つける必要があります。
別の解決策は、証拠を反変にすることですが、これは推論Nothing
やその他の問題など、多くの問題を引き起こします (私の実際のコードは、この単純化された例よりも複雑です)。
どうすればこれを正しく機能させることができますか?