我有一个如下所示的域名模型:
case class Account(id: Int, name: String)
trait BalanceTotal {
def balance: BigDecimal
}
我的目标是拥有一个简单,轻量级的Account
案例类,然后是一个增强的类Account with BalanceTotal
,它只会在执行余额计算的方法中创建(这很昂贵)。
通过这种结构,我可以静态地确保在我拥有轻量级对象时,我永远不会指望存在余额。我当然知道Option
,但我希望类型检查器阻止代码使用轻量级对象,我需要富含平衡的对象,反之亦然,我不认为{ {1}}给了我那个。
无论如何,我想做的是:
Option
但是失败了:
for{ Account(id,name) <- accounts } {
yield Account(id, name) with BalanceTotal {
override val balance = BigDecimal(44)
}
}
如果我尝试使用';' expected but 'with' found
代替new Account
,我会:
Account
我认为它与使用案例类的voodoo有关。
我可以做我想做的事吗?
更新:经过进一步考虑,我猜这与禁止案例类继承有关。但我确实需要案例类魔术:我依赖生成的super constructor arguments cannot reference unconstructed `this`
和apply
方法来实现我的ScalaQuery映射。
答案 0 :(得分:2)
对我来说没关系:
>scala
Welcome to Scala version 2.9.1.final (Java HotSpot(TM) 64-Bit Server VM, Java 1.
7.0).
Type in expressions to have them evaluated.
Type :help for more information.
scala> :paste
// Entering paste mode (ctrl-D to finish)
case class Account(id: Int, name: String)
trait BalanceTotal {
def balance: BigDecimal
}
val enrichedAccount = new Account(1, "foo") with BalanceTotal {
override val balance = BigDecimal(44)
}
// Exiting paste mode, now interpreting.
defined class Account
defined trait BalanceTotal
enrichedAccount: Account with BalanceTotal = Account(1,foo)
答案 1 :(得分:1)
由于缺少new
,您的示例无效。 Account(id, name)
实际上会调用Account.apply(id, name)
并返回Account
,您无法调用with
。 new Account(id, name) with BalanceTotal
被转换为匿名类,使用Account
扩展BalanceTotal
。希望这有助于理解您的代码无法正常工作的原因。
答案 2 :(得分:1)
你的问题不是因为而是收益。使用括号如下,它将起作用:
for ( Acount(id, name) <- accounts) yield
(new Account(id, name) with BalanceTotal {
override val balance = BigDecimal(42)
})