0

我正在编写一个实现任意对象的二维矩阵的 Scala 类。我需要这个类比嵌套的对象对更专业IndexedSeq,但是扩展一个集合类是多余的,所以我正在编写自己的。为了从我的矩阵类中的方法返回正确的类型,我使用了隐式构建器习语,但在运行时我得到一个我不明白的“找不到参数的隐式值”错误。

我的矩阵类的精简版本如下所示。

trait MatrixBuilder[V, M <: Matrix[V]] {
  def apply(values: IndexedSeq[IndexedSeq[V]]): M
}

abstract class Matrix[V](values: IndexedSeq[IndexedSeq[V]]) extends Function2[Int, Int, V] {

  def apply(row: Int, col: Int): V = values(row)(col)

  def set[M <: Matrix[V]](row: Int, col: Int, value: V)(implicit builder: MatrixBuilder[V, M]): M =
    builder(values.updated(row, values(row).updated(col, value)))
}

case class IntMatrix(values: IndexedSeq[IndexedSeq[Int]]) extends Matrix[Int](values)

object IntMatrix {
  def apply(n: Int) = new IntMatrix(IndexedSeq.fill(n, n)(0))

  implicit object IntMatrixBuilder extends MatrixBuilder[Int, IntMatrix] {
    def apply(values: IndexedSeq[IndexedSeq[Int]]) = IntMatrix(values)
  }
}

我希望该set函数设置指定的单元格,然后返回正确类型的新矩阵。所以我希望IntMatrix(2).set(0,0,5)返回一个IntMatrix在除 (0,0) 之外的所有单元格中都为零的对象,它应该有一个 5。相反,我在运行时收到以下错误。

error: could not find implicit value for parameter builder: MatrixBuilder[Int,M]
    IntMatrix(2).set(0,0,5)

我在这里做错了什么?


正如pedrofurla在下面指出的那样,如果您首先运行该行,则该代码确实可以在 REPL 中运行import IntMatrix._。并且查看集合文档,使用构建器的源代码中似乎有类似的导入语句。我尝试在我的IntMatrix班级中添加一个。

case class IntMatrix(values: IndexedSeq[IndexedSeq[Int]]) extends Matrix[Int](values) {
    import IntMatrix._
}

但这没有效果。(事实上​​,我的 IDE IntelliJ 将此标记为未使用的导入语句。)

为了比较,我从上面逐字链接的集合文档中复制了 RNA 序列示例。该import RNA._行没有被标记为多余的,并且所有操作都返回正确的类型。如果答案是我需要添加一个import IntMatrix._,我不知道该放在哪里。

4

1 回答 1

1

这个小代码在这里工作:

scala> import IntMatrix._
import IntMatrix._

scala> IntMatrix(2).set(0,0,5)
res1: Mat.IntMatrix = <function2>

隐式参数由调用站点中的编译器填充,因此它们必须在set被调用的范围内可用。

于 2013-01-27T11:12:40.737 回答