scala伴随对象应用中是否有比Companion.forBla.withBla.withBla更好的构建器模式?

时间:2013-12-17 09:15:54

标签: scala builder

如果我有多种方法来创建对象,我应该在我的随播对象中使用多个 apply 方法吗?如果有多个应用方法,我会更难看一个。但是,如果我有多种方法来构造我的对象,这意味着我将回到我在java中使用的标准构建器模式。 (的 Companion.forBla.withBla.withBla

2 个答案:

答案 0 :(得分:6)

您需要区分builderfactory method

构建器用于避免伸缩构造函数,您可以在其中创建多个构造函数,以使用户能够创建具有不同属性的对象。因此,在伴随对象中使用多个apply方法会导致这种伸缩构造函数,并可能导致混乱的代码(反模式)。一个例子是:

case class ComplexClass(foo: String, bar: Int)

case class ComplexClassBuilder(foo: Option[String], bar: Option[Int]){
  def withFoo(f: String) =
    this.copy(foo = Some(f))

  def withBar(b: Int) =
    this.copy(bar = Some(b))

  def finish = {
    // this is the place to decide what happens if there are missing values
    // possible ways to handle would be to throw an exception, return an option or use defaults
    ComplexClass(foo getOrElse ":D", bar getOrElse 42)
  }
}

工厂方法通常用于启用多态apply方法是实现工厂方法的好方法

trait C

case class Foo() extends C

case class Bar() extends C

object C {
  def apply(isAwesome: Boolean): C = isAwesome match {
    case true  => Foo()
    case false => Bar()
  }
}

但与往常一样,那些是模式而不是规则。通常使用一个或两个apply方法来允许创建具有不同参数的对象。但是,如果需要设置许多不同的值,则应避免使用apply方法并实现构建器。

答案 1 :(得分:2)

你的问题听起来像是一种观点或品味。 (为什么你认为有多个apply方法是丑陋的?)。

方法参数可以有默认值,参数可以命名为:

class MySomething(val one: String, val two: Int)

object MySomething {
  def apply(one: String = "hello", two: Int = 0) = new MySomething(one, two)
}

// Creates a MySomething with one = "hello" and two = 0
val a = MySomething()

// Creates a MySomething with one = "bye" and two = 0
val b = MySomething("bye")

// Creates a MySomething with one = "hello" and two = 2
val c = MySomething(two = 2)
相关问题