Scala:如何在伴随对象中定义构造函数参数的默认值?

时间:2017-07-12 14:31:22

标签: scala constructor

以下Scala代码无法在Scala REPL 2.11.6中编译:

object Foo {
  val DefaultSize: Int = 10
}

class Foo(size: Int = Foo.DefaultSize)

编译错误是:

value DefaultSize is not a member of object Foo
class Foo(size: Int = Foo.DefaultSize)

使用Scala 2.11进行测试。这一点特别奇怪,因为它完全遵循这里接受的答案(2012年):Use method return value as default constructor parameter in Scala,现在也没有编译。那么如何实现预期的行为?

1 个答案:

答案 0 :(得分:3)

作为explained in Programming in Scala,这是因为Scala REPL为您键入的每个新语句创建了一个新的嵌套范围。这意味着您的代码被解释为:

object Foo {
  val DefaultSize: Int = 10
}
{
  class Foo(size: Int = Foo.DefaultSize)
}

虽然必须在同一源文件中定义类及其伴随对象的the same book mentions,但它们似乎必须在同一范围内,因为does not compile with scalac以上的代码块。 / p>

我知道在REPL中解决这个问题的两种方法。如其他人所述,您可以在定义类和伴随对象之前进入:paste模式。或者,您可以将两者放在同一范围内,例如,通过在对象中定义它们:

object My {
   object Foo {
     val DefaultSize: Int = 10
   }
   case class Foo(size: Int = Foo.DefaultSize)
}

现在您可以按预期使用Foo

scala> new My.Foo()
res0: My.Foo = Foo(10)
scala> new My.Foo(20)
res1: My.Foo = Foo(20)

(我使class Foo成为case class,以便在最后一个代码块中获得简洁的REPL结果。但是,答案无需更改即可。)