重构样板类型约束

时间:2013-10-09 01:21:27

标签: scala

我有一个带有一堆相关例程的对象,它们的所有声明看起来都是一样的,比如

object Sorting {
  def qsort[a <% Ordered[a]] ....

  def partition[a <% Ordered[a]] ...

  def qselect[a <% Ordered[a]] ...
}

有没有办法在一个地方指定类型约束,并将声明简化为qsort[a](xs: Stream[a])或更好qsort(xs: Stream[a])

暂时我决定使用隐式类

object Implicits {
  implicit class SortableArray[a <% Ordered[a]](xs: Array[a]) {
    def qsort = {...}
  }
}

object Application {
  import Implicits._
  def main(args: Array[String]) = {
    val xs = Array(1,2,3)
    xs.qsort
  }
}

2 个答案:

答案 0 :(得分:3)

很遗憾,您无法将类型声明为type U[T] = T <% Ordered[T]。这不起作用,甚至不会编译。

但是,您可以将一些解决方法应用于您的代码

设想这个思维流程:

如上所述here

def f[A <% B](a: A) = a.bMethod

相同

def f[A](a: A)(implicit ev: A => B) = a.bMethod

和这个

def g[A : B](a: A) = h(a)

相同

def g[A](a: A)(implicit ev: B[A]) = h(a)

回到你的例子:

def qsort[A <% Ordered[A]] = ???

...被翻译为:

def qsort[A](implicit ev: A => Ordered[A]) = ???

...现在您可以引入类型参数,如:

type O[A] = A => Ordered[A]

...并将其用作:

def gsort[A] (implicit ev: O[A])

......可以简化为:

def gsortX[A : O]

然后您可以编写所有代码:

<强>之前

object Sorting {

  def qsort[A <% Ordered[A]] = ???

  def partition[A <% Ordered[A]] = ???

  def qselect[A <% Ordered[A]] = ???
}

<强>后

object Sorting {

  type O[A] = A => Ordered[A]

  def qsort[A: O] = ???

  def partition[A: O] = ???

  def qselect[A: O] = ???
}

甚至更好地使用特质

trait Sorting[A] {
  type O = A => Ordered[A]
  implicit def f : O

  def qsort = ???

  def partition = ???

  def qselect = ???
}

我希望这会有所帮助:)

答案 1 :(得分:1)

没有别名,如this question中所述。该视图绑定实际上为每个方法添加了一个隐式参数,这些参数不容易被抽象为类型别名。