带有Scala中可选字段的Case Classes

jey*_*ypi 25 scala

例如,我有这个案例类:

case class Student (firstName : String, lastName : String)
Run Code Online (Sandbox Code Playgroud)

如果我使用这个case类,那么向case类中的字段提供数据是否可选?例如,我会这样做:

val student = new Student(firstName = "Foo")
Run Code Online (Sandbox Code Playgroud)

谢谢!

om-*_*nom 33

你很亲密:

case class Student (firstName : String = "John", lastName : String = "Doe")

val student = Student(firstName = "Foo")
Run Code Online (Sandbox Code Playgroud)

另一种可能性是部分应用功能:

case class Student (firstName : String, lastName : String)

val someJohn = Student("John", _: String)
//someJohn: String => Student = <function1>

val johnDoe = someJohn("Doe")
//johnDoe: Student = Student(John,Doe)
Run Code Online (Sandbox Code Playgroud)

要完成,您可以创建一些默认对象,然后更改一些字段:

val johnDeere = johnDoe.copy(lastName="Deere")
//johnDeer: Student = Student(John,Deere)
Run Code Online (Sandbox Code Playgroud)


tgr*_*tgr 32

如果您只是想在没有默认信息的情况下错过第二个参数,我建议您使用Option.

case class Student(firstName: String, lastName: Option[String] = None)
Run Code Online (Sandbox Code Playgroud)

现在您可以这样创建实例:

Student("Foo")
Student("Foo", None)            // equal to the one above
Student("Foo", Some("Bar"))     // neccesary to add a lastName
Run Code Online (Sandbox Code Playgroud)

为了使它可以按你的意愿使用,我将添加一个隐含的:

object Student {
  implicit def string2Option(s: String) = Some(s)
}
Run Code Online (Sandbox Code Playgroud)

现在,您可以通过以下方式调用它:

import Student._

Student("Foo")
Student("Foo", None)
Student("Foo", Some("Bar"))
Student("Foo", "Bar")
Run Code Online (Sandbox Code Playgroud)

  • Noooooooo!不要在代码中使用隐式转换,尤其不要在String和Option等常见类型之间使用.如果必须"更容易",请为Student的apply方法添加一个重载. (46认同)

aka*_*ppi 8

我会看到通常这两种方式.

1.默认参数

case class Student (firstName : String, lastName : String = "")

Student("jeypijeypi")   # Student(jeypijeypi,)
Run Code Online (Sandbox Code Playgroud)

替代建设者

case class Student (firstName : String, lastName : String)

object Student {
    def apply(firstName: String) = new Student(firstName,"")
}

Student("jeypijeypi")   # Student(jeypijeypi,)
Run Code Online (Sandbox Code Playgroud)

哪一个更好取决于具体情况.后者为您提供更多自由:您可以使任何参数可选,甚至更改其顺序(不推荐).我想,默认参数总是需要在参数列表的末尾.您也可以将这两种方式结合起来.

注意:在替代构造函数中,您需要new将编译器指向实际的构造函数.通常new不用于案例类.