Scala Currying:使用部分函数覆盖空参数的函数

时间:2013-12-11 15:24:05

标签: scala override abstract currying partialfunction

我正在尝试使用部分函数来实现/覆盖具有空输入参数的函数。最好的解释是这个非工作的最小例子:

trait T
trait TFactory {
  def build(): T
}

class A(someParameter: Int) extends T

object A extends TFactory {
  def build(someParameter: Int)(): T = new A(someParameter)
}

编译器抱怨:object creation impossible, since method build in trait TFactory of type ()T is not defined,这是有道理的,因为构建类型是(Int)()T。我的下一个想法是将build的类型明确地赋予一个函数,该函数采用空参数并返回T,即:

trait T 
trait TFactory {
  def build: () => T    // what about empty parenthesis after build?
}

class A(someParameter: Int) extends T 

object A extends TFactory {
  def build(someParameter: Int): (() => T) = (() => new A(someParameter))
}

现在很明显build的类型是() => T。令我惊讶的是,编译器现在抱怨object creation impossible, since method build in trait TFactory of type => () => T is not defined(注意类型突然以=>开头)。在函数定义的末尾拼命添加空括号也无济于事。

我如何说服我的编译器这些类型实际上是相同的?

澄清:

我的主要目标是实现T的无参数初始化,而无需工厂工厂。例如:

val t = A(33).build()      // if this is possible, I though it might be possible to have:
val t = A.build(33)()

结论:

我认为这是不可能的,因为抽象函数只是确定build函数必须采用多少个参数块。换句话说:您不能通过函数实现抽象函数,其部分应用程序恰好与您尝试实现的函数具有相同的签名。

1 个答案:

答案 0 :(得分:1)

我不确定你想要达到什么目标。假设您的TFactory已在第一个示例中给出:

trait T

trait TFactory {
  def build(): T
}

然后build方法显然不能采用任何参数。如果您想配置工厂,您可以拥有工厂工厂:

class A(x: Int) extends T

object A {
  def apply(x: Int): TFactory = new TFactory {
    def build() = new A(x)
  }
}

val factory = A(33)
val t = factory.build()

如果您将TFactory定义为()T的功能,则可以使用currying

type TFactory = () => T

object A {
  def apply(x: Int)(): T = new A(x)
}

val factory: TFactory = A(33) _
val t = factory()