`def` vs `val` vs `lazy val` evaluation in Scala

Ivan picture Ivan · Feb 26, 2012 · Viewed 21.8k times · Source

Am I right understanding that

  • def is evaluated every time it gets accessed

  • lazy val is evaluated once it gets accessed

  • val is evaluated once it gets into the execution scope?

Answer

om-nom-nom picture om-nom-nom · Feb 26, 2012

Yes, but there is one nice trick: if you have lazy value, and during first time evaluation it will get an exception, next time you'll try to access it will try to re-evaluate itself.

Here is example:

scala> import io.Source
import io.Source

scala> class Test {
     | lazy val foo = Source.fromFile("./bar.txt").getLines
     | }
defined class Test

scala> val baz = new Test
baz: Test = Test@ea5d87

//right now there is no bar.txt

scala> baz.foo
java.io.FileNotFoundException: ./bar.txt (No such file or directory)
    at java.io.FileInputStream.open(Native Method)
    at java.io.FileInputStream.<init>(FileInputStream.java:137)
...

// now I've created empty file named bar.txt
// class instance is the same

scala> baz.foo
res2: Iterator[String] = empty iterator