[英]Curried apply in trait companion object
两个问题:
1)当apply
函数被咖喱化时,为什么我不能在BaseTrait
伴随对象中拥有这两个apply
方法(注意,当它们被非咖喱化时,带有两个参数,它可以工作)?
2)如何实现此功能:多个可应用的套用方法?
trait BaseTrait[T, U] {
def name: String
def tryMe(record: T): Option[U]
}
object BaseTrait {
// can't have both apply methods when curried
def apply[T](s: String)(f: T => Option[Long]): LongTrait[T] =
new LongTrait[T] {
override val name: String = s
override def tryMe(record: T): Option[Long] = f(record)
}
def apply[T](s: String)(f: T => Option[Boolean]): BooleanTrait[T] =
new BooleanTrait[T] {
override val name: String = s
override def tryMe(record: T): Option[Boolean] = f(record)
}
}
trait LongTrait[T] extends BaseTrait[T, Long] {
override def tryMe(record: T): Option[Long]
}
trait BooleanTrait[T] extends BaseTrait[T, Boolean] {
override def tryMe(record: T): Option[Boolean]
}
它可以正常编译,但是会引发运行时错误:
scala> BaseTrait("test") { s: String => Option(s.toBoolean) }
<console>:13: error: ambiguous reference to overloaded definition,
both method apply in object BaseTrait of type [T](s: String)(f: T =>
Option[Boolean])BooleanTrait[T]
and method apply in object BaseTrait of type [T](s: String)(f: T =>
Option[Long])LongTrait[T]
match argument types (String)
BaseTrait("test") { s: String => Option(s.toBoolean) }
如果您颠倒当前参数的顺序,以使它们在第一个参数中不同,则apply方法可以成功调用。
object BaseTrait {
// can't have both apply methods when curried
def apply[T](f: T => Option[Long])(s: String): LongTrait[T] =
new LongTrait[T] {
override val name: String = s
override def tryMe(record: T): Option[Long] = f(record)
}
def apply[T](f: T => Option[Boolean])(s:String): BooleanTrait[T] =
new BooleanTrait[T] {
override val name: String = s
override def tryMe(record: T): Option[Boolean] = f(record)
}
}
BaseTrait { s:String => Option(s.toBoolean) }("test")
res58: BooleanTrait[String] = ammonite.$sess.cmd57$BaseTrait$$anon$2@e39317d
如评论中所述, 这似乎是该语言的一个极端案例 。 在以“ Wont-Fix”状态关闭的引用问题中,以下更简单的代码也表现出相同的歧义引用问题。
object Foo {
def bar(i: Int) = println(i)
def bar(i: Int) (f: Float) = println(i*f)
}
根据Scala语言创建者Martin Odersky的说法,
“我只是在上面写道,规范中没有尝试做这样的事情。我向您挑战,请您提供一套完整且可确定的规则来做到这一点。”
因此看来,由于难以实施必要的检查,因此即使无法随后引用这些方法,也无法阻止这些方法的编译。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.