Scala构造函数重载?


Answers:


186

值得一提的是,Scala中的辅助构造函数必须首先调用主构造函数(如landon9720的答案),或者将同一个类中的另一个辅助构造函数作为其第一个动作。他们不能像在Java中那样简单地显式或隐式调用超类的构造函数。这样可以确保主构造函数是该类的唯一入口。

class Foo(x: Int, y: Int, z: String) {  
  // default y parameter to 0  
  def this(x: Int, z: String) = this(x, 0, z)   
  // default x & y parameters to 0
  // calls previous auxiliary constructor which calls the primary constructor  
  def this(z: String) = this(0, z);   
}

@乔恩·麦考利夫:不好的例子吗?没有第二和第三构造函数,用户仍然可以调用,new Foo(x=2,z=4)并且new Foo(z=5)如果您将第一行更改为class Foo(x: Int = 0, y: Int = 0, z: String) {
user2987828 2014年

直到Scala 2.8,命名/默认参数才出现。
乔恩·麦考利夫

2
值得一提的是如何使用重载构造函数。new即使对于案例类,关键字也是必需的,这并非无关紧要。
Readren '18

33
 class Foo(x: Int, y: Int) {
     def this(x: Int) = this(x, 0) // default y parameter to 0
 }

16

从Scala 2.8.0开始,您还可以使用构造函数和方法参数的默认值。像这样

scala> class Foo(x:Int, y:Int = 0, z:Int=0) {                           
     | override def toString() = { "Foo(" + x + ", " + y + ", " + z + ")" }
     | }
defined class Foo

scala> new Foo(1, 2, 3)                                                    
res0: Foo = Foo(1, 2, 3)

scala> new Foo(4)                                                          
res1: Foo = Foo(4, 0, 0)

具有默认值的参数必须位于参数列表中没有默认值的参数之后。


3
但是,这对于非平凡的默认设置无效。因此class Foo(val x:Int, y:Int=2*x)不起作用。
subsub

@JörgenLundberg:您编写的具有默认值的参数必须位于参数列表中没有默认值的参数之后。是错误的,new Foo(x=2,z=4)将打印Foo(2,0,4)
user2987828 2014年

@ user2987828我的意思是您不能编写新的Foo(12,x = 2),而必须编写新的Foo(x = 2,12)。你可以写新的Foo(12,Y = 2),那么你会得到美孚(12,2,0)
约尔根伦德伯格

10

在查看代码时,我突然意识到我确实在重载了构造函数。然后,我想起了这个问题,然后回来给出另一个答案:

在Scala中,您不能重载构造函数,但是可以使用函数来做到这一点。

同样,许多人选择将apply伴随对象的功能设置为相应类的工厂。

使此类成为抽象并重载apply要实例化该类的函数,您就有了重载的“构造函数”:

abstract class Expectation[T] extends BooleanStatement {
    val expected: Seq[T]}

object Expectation {
    def apply[T](expd:     T ): Expectation[T] = new Expectation[T] {val expected = List(expd)}
    def apply[T](expd: Seq[T]): Expectation[T] = new Expectation[T] {val expected =      expd }

    def main(args: Array[String]): Unit = {
        val expectTrueness = Expectation(true)}
}

请注意,我明确定义了每个apply要返回的内容Expectation[T],否则它将返回duck-typed Expectation[T]{val expected: List[T]}


0

试试这个

class A(x: Int, y: Int) {
  def this(x: Int) = this(x, x)
  def this() = this(1)
  override def toString() = "x=" + x + " y=" + y
  class B(a: Int, b: Int, c: String) {
    def this(str: String) = this(x, y, str)
    override def toString() =
      "x=" + x + " y=" + y + " a=" + a + " b=" + b + " c=" + c
  }
}
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.