我有一个数组Any
(在现实生活中,这是一个星火Row
,但它足以分离的问题)
object Row {
val buffer : Array[Any] = Array(42, 21, true)
}
我想申请在其元素的一些操作。 所以,我已经定义了一个简单的ADT定义compute
上某种类型的操作A
trait Op[A] {
def cast(a: Any) : A = a.asInstanceOf[A]
def compute(a: A) : A
}
case object Count extends Op[Int] {
override def compute(a: Int): Int = a + 1
}
case object Exist extends Op[Boolean] {
override def compute(a: Boolean): Boolean = a
}
鉴于本人所有操作的列表,我知道这是操作应用到每一个元素,让我们使用这些操作。
object GenericsOp {
import Row._
val ops = Seq(Count, Exist)
def compute() = {
buffer(0) = ops(0).compute(ops(0).cast(buffer(0)))
buffer(1) = ops(0).compute(ops(0).cast(buffer(1)))
buffer(2) = ops(1).compute(ops(1).cast(buffer(2)))
}
}
按照设计,对于给定的运算,类型之间对准cast
和combine
。 但不幸的是下面的代码不会编译。 错误的是
Type mismatch, expected: _$1, actual: AnyVal
有没有一种方法,使工作?
我用抽象类型成员,而不是类型参数找到了解决办法。
object AbstractOp extends App {
import Row._
trait Op {
type A
def compute(a: A) : A
}
case object Count extends Op {
type A = Int
override def compute(a: Int): Int = a + 1
}
case object Exist extends Op {
type A = Boolean
override def compute(a: Boolean): Boolean = a
}
val ops = Seq(Count, Exist)
def compute() = {
val op0 = ops(0)
val op1 = ops(1)
buffer(0) = ops(0).compute(buffer(0).asInstanceOf[op0.A])
buffer(1) = ops(0).compute(buffer(1).asInstanceOf[op0.A])
buffer(2) = ops(1).compute(buffer(2).asInstanceOf[op1.A])
}
}
有没有更好的办法 ?