Scala和UnionType绑定到泛型类型

时间:2014-06-25 07:52:57

标签: scala scalaz

情景:

我们有不同的类ABC,它们具有 no 公共基类,但它们都提供了一个方法foo,它接受一个与类本身相同类型的参数,并返回类型Boolean的值。

然后我们想要提出一个相当复杂的方法bar,它接受​​三个参数,它们都应该是相同的类型,即所有三个参数都是A类型,或{{1 }},或B但不是它们的混合物。

这个想法(不编译):

C

当然,我可以通过实施方法import scalaz.UnionTypes._ class A { def foo(y: A): Boolean = ??? } class B { def foo(y: B): Boolean = ??? } class C { def foo(y: C): Boolean = ??? } class Foo { type T <: t[A]#t[B]#t[C] def bar(x: T, y: T, z: T) = x.foo(y) && y.foo(z) // do more complex stuff } 三次来解决这个问题

bar

但由于它是一个相当复杂的方法,我不想复制代码。

我原本希望来自scalaz的UnionTypes在这种情况下可能有所帮助,但是我得到了一个编译时错误。有人知道如何解决这个问题吗?

1 个答案:

答案 0 :(得分:3)

使用type class pattern

trait CanFoo[T] {
  def foo(x: T, y: T): Boolean
}

object CanFoo {
  implicit val ACanFoo: CanFoo[A] = new CanFoo[A] {
    def foo(x: A, y: A) = x.foo(y)
  }

  // similar definitions for B and C
}

class Foo {
  def bar[T](x: T, y: T, z: T)(implicit canFoo: CanFoo[T]) = 
    canFoo.foo(x, y) && canFoo.foo(y, z)
}