1

我有以下情况:

sealed abstract class Type(val inUse: Boolean)

case class IntTy(override val inUse: Boolean) extends Type(inUse)

case class TupleTy(override val inUse: Boolean, elems: Type*) extends Type(inUse) {
  def this(elems: Type*) = this(false, elems:_*)
}

在 Scala 2.8.0 这工作得很好,我可以创建一个新的 TupleTy 实例:

TupleTy(IntTy(false))

但是,我刚刚更新到 Scala 2.9.1 final 并且它不再有效。我现在收到以下错误:

error: type mismatch;
found   : IntTy
required: Boolean
              TupleTy(IntTy(false))
                           ^

这是一个错误还是我错过了什么?

4

2 回答 2

5

我不确定它是否适用于 2.8.0。

您已经定义了一个额外的构造函数,但没有定义一个额外的工厂方法。

new TupleTy(IntTy(false)) // works as expected

编辑

这是一个可能的解决方法

case class TupleTy(override val inUse: Boolean = false)(elems: Type*) extends Type(inUse)

现在你可以做这样丑陋的事情,但你不应该这样做。不,真的,你不应该。

TupleTy()(IntTy(false))
于 2011-09-02T14:34:49.850 回答
3

用“new”创建你的 TupleTy(就像一个普通的类)可以:

scala> new TupleTy(IntTy(false))
res3: TupleTy = TupleTy(false,WrappedArray(IntTy(false)))

案例类的其他构造函数需要用“new”调用,因为(与默认构造函数不同)不会“翻译”为伴随对象上的应用方法。请注意,“unapply”也不会生成,因此 TupleTy 上的模式匹配可能无法按预期工作。

这是关于 scala-lang.org 的一些背景讨论,关于为什么 scala 编译器没有被增强来处理多个案例类构造函数。

编辑你可以自己创建额外的“应用”,如果你想:

object TupleTy {
  def apply(elems: Type*) = new TupleTy(false, elems:_*)
}

有了它,你可以这样做:

scala> TupleTy(IntTy(false))
res4: TupleTy = TupleTy(false,WrappedArray(IntTy(false)))
于 2011-09-02T14:35:24.227 回答