【发布时间】:2015-05-19 22:58:30
【问题描述】:
如果有人能向我解释为什么以下会导致问题,我将不胜感激。我创建了一个小例子来演示这个问题:
我有一个正在用 sbt 构建的项目,build.sbt 如下:
lazy val root = (project in file(".")).
settings(
name := "Test",
version := "1.0.0",
scalaVersion := "2.11.5",
libraryDependencies += "org.scalatest" %% "scalatest" % "2.2.4" % Test
)
和 src/main/scala 中的 Test.scala:
object Test extends App
{
private val map = Map(1 -> 2)
def access = map(1)
println(access)
}
和 src/test/scala 中的 TestSpec.scala(使用 scalatest):
import org.scalatest.FlatSpec
class TestSpec extends FlatSpec
{
"A Test" should "allow access to the map" in
{
assert(Test.access == 2)
}
}
如果我 sbt run 则 '2' 会按预期打印出来。如果我 sbt test 然后我得到一个 NullPointerException 并且测试失败:
[info] TestSpec:
[info] A Test
[info] - should allow access to the map *** FAILED ***
[info] java.lang.NullPointerException:
[info] at Test$.access(Test.scala:4)
[info] at TestSpec$$anonfun$1.apply$mcV$sp(TestSpec.scala:7)
etc.
这是因为在 TestSpec 访问时 map 为空。我可以通过将地图更改为惰性 val 或 def 来解决此问题,但我想了解更多关于此处的初始化顺序发生了什么以及将来如何避免此类事情的详细信息。如果我尝试使用 src\main\scala 中的另一个源文件访问它,我没有任何问题,并且我想避免以这种方式更改变量的定义来解决此类问题。
谢谢
【问题讨论】: