deltanovember
deltanovember

Reputation: 44091

Why does the following Scala code throw a NullPointerException?

If I instantiate Base2 it runs fine

class Base2 {

  class Benchmark {
    def onTrade() {
      println("base onTrade")
    }
  }

  protected val benchmark = new Benchmark
  benchmark.onTrade
}

class Base3 extends Base2 {

  override val benchmark = new Benchmark {
    override def onTrade() {
      println("sub onTrade")
    }
  }
}

// to run
new Base3

Exception info:

java.lang.NullPointerException
    at Base2.<init>(<console>:16)
    at Base3.<init>(<console>:19)
    at .<init>(<console>:10)
    at .<clinit>(<console>)
    at .<init>(<console>:11)
...

Upvotes: 2

Views: 560

Answers (2)

user166390
user166390

Reputation:

Base2 is initialized first at which time benchmark.onTrade is executed, however the member benchmark from Base3 (not Base2!) is being used because of the override (benchmark in Base2 is actually initialized first, but it doesn't matter because the other benchmark is being "bound" to!). I am fairly certain this has to do with the val being virtual...

Base3's initialization won't start (or resume?) until after Base2's is finished and thus Base3.benchmark is still null at benchmark.onTrade.

FWIW, a "lazy val" seems to "fix" the issue.

Happy coding.

Upvotes: 4

Preet Sangha
Preet Sangha

Reputation: 65556

I don't know scala but could it be something like:

Base3's benchmark instance is not constructed until after all the code in Base2 (benchmark.onTrade) has been executed?

Upvotes: 1

Related Questions