scala:有构造函数区分apply和implicit参数吗?

时间:2011-05-20 08:17:56

标签: scala

我有一个这样的课程:

class A(arg: Int)(implicit i: Boolean) {
  def apply(v: Double): this.type = {
    // do stuff
    this
  }
}

我想通过初始化它并在同一行中调用apply来创建它的实例:

implicit val i = false
val a = A(arg=1)(v=2.0) // doesn't work
val a2 = (A(arg=1))(v=2.0) // doesn't work

不幸的是,编译器假定v = 2.0是针对隐式参数而不是针对apply()。我尝试了许多不同的语法,插入{}和(),但没有一个工作。我意识到v可以移动到构造函数中,但在我的情况下,这不是一个选项,因为A是子类,我不想将v添加到每个子类构造函数。有没有办法实现这个目标?感谢。

2 个答案:

答案 0 :(得分:5)

“丑陋但似乎有用”怎么样......

class A(arg: Int)(implicit i: Boolean) {
  def apply(v: Double): this.type = this
}
implicit val i = false
// removing the :A makes this fail to run on simplyscala
val a1 = (new A(arg=1) : A)(v=2.0)
// also works with explicit method name
val a2 = new A(arg=1).apply(v=2.0)
// and works without implicit being ... implicitized
val a = new A(arg=1)(i)(v=2.0)

老实说,不知道:-)但是,考虑一下这可能是一些见解:

val a = (new A(arg=1))(2.0)
error: type mismatch;
 found   : Double(2.0)
 required: Boolean
       val a = (new A(arg=1))(2.0)

哇!

快乐的编码。

答案 1 :(得分:4)

(我假设您在配对对象中有一个构造函数方法,因为您没有使用new A。)

一个选项是将它写在两行:

val atmp = A(1)
val a = atmp(2.0)

......但那肯定不是你想要的。另一个同样不满意的选择是

val a = A(1)(implicitly)(2.0)

如果你可以忍受。也许最简单的方法就是明确地调用apply

val a = A(1).apply(2.0)

最后,您可以向配对对象添加一个新的构造函数方法来处理所有这些:

object A {
  def apply(arg: Int, v: Double)(implicit i: Boolean) = A(arg)(i)(v)
}

val a = A(1, 2.0)