1

クラスが表現型を持つ特定の特性でパラメーター化されている場合にのみ、インスタンスのコピーを返す必要がある型パラメーターとメソッドを持つクラスがあるとします。私はそれをかなり簡単に実現できます。私ができないことは、そのメソッドの適切な戻り値の型を置くことです:

case class Foo[+A](a: A) {
  // Compiles
  def gotFooBar(implicit evidence: A <:< Bar[_]) = copy(a = a.Copy())

  // Does not compile
  def gotFooBar(implicit evidence: A <:< Bar[_]): Foo[A] = copy(a = a.Copy())
}

trait Bar[+B <: Bar[B]] {
  def Copy(): B // Return underlying type
}

case class Grill() extends Bar[Grill] {
  def Copy() = Grill()
}

その関数の戻り値の型は何ですか? または、おそらくもっと重要なことですが、それが戻り値の型になるようにどのように型を設定すればよいでしょうか? 誰かが実際の戻り値の型が のスーパータイプになる方法を指摘できますFoo[A]か?

4

2 に答える 2

2

まあ、必要なのは を呼び出した結果としてBar[_]得られるだけだからです。メソッドの型パラメーターが必要です。Anya.CopygotFooBar

case class Foo[+A](a: A) {
   def gotFooBar[B <: Bar[B]](implicit evidence: A <:< B): Foo[B] = {
      val bar = a: B
      copy(a = bar.Copy())
   }
}

Foo[B]2 番目の質問は、それが のスーパータイプであることを強制する方法ですFoo[A]Aの下限として追加するだけですB

def gotFooBar[B >: A <: Bar[B]](implicit evidence: A <:< B): Foo[B]
于 2012-07-21T00:32:43.390 に答える
0

これは、@ 0__ による回答に対するフォローアップの回答です。Aマニフェストが関連付けられている場合、状況はもう少し複雑になります。

case class Foo[+A : Manifest](a: A)

メソッド型パラメーターBには、マニフェストも必要です (使用しない場合でも)。マニフェスト ( ) を追加する通常の方法も機能しません。これは、メソッドに暗黙のパラメーター (この場合は ): Manifestがある場合は許可されないためです。implicit evidenceただし、次のように、マニフェストを暗黙的なパラメーター リストに入れることができます。

def gotFooBar[B >: A <: Bar[B]]
  (implicit m: Manifest[B], evidence: A <:< B): Foo[B] =
  copy(a = a.Copy())
于 2012-07-22T16:31:08.730 に答える