以下代码在 scala2 中按 (I) 预期工作,但在 scala3 中生成编译时错误。我试图在《Scala 编程》第五版和网络中找到解释,但失败了。有什么见解吗?
object Main {
def main(args:Array[String]): Unit = {
val foo = new Foo(7)
println(foo.double) // 14
val bar = new Foo(8) {
def triple:Int = this.i * 3
}
println(bar.double) // 16
println(bar.triple) // 24 in scala2; compile error in scala3
}
}
class Foo(val i:Int) {
def double:Int = i*2
}
编译错误:
-- [E008] Not Found Error: /tmp/example.scala:12:20 ----
12 | println(bar.triple)
| ^^^^^^^^^^
| value triple is not a member of Foo
如果您使用 编译代码
scala -Xprint:typer
,您将看到val bar
现在Foo
在 Scala 3 中明确具有类型:将此与 Scala 2 进行对比,其中
bar
获取细化类型Foo { def triple: Int }
:所以就是
要实现 Scala 2 的行为,您可以
Bar
显式引入一个新类:完整的可编译代码:
至于为什么它是推断
Foo
而不是Foo { def triple: Int }
- 我不太确定,我猜他们最终发现这种行为与其他语言功能配合得更好。你如何解释
val x = "hello"
推论x: String
和不推论x: "hello"
?Scala 3 迁移指南对此进行了介绍,网址为https://docs.scala-lang.org/scala3/guides/migration/incompat-type-in ference.html#reflective-type :