Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why does Scala compiler reject function body with no leading space?

Tags:

scala

I found this very confusing.

scala> val a = (x:Boolean)=>!x
<console>:7: error: not found: value x
       val a = (x:Boolean)=>!x
                ^

scala> val a = (x:Boolean)=> !x
a: Boolean => Boolean = <function1>

The only difference between the two is the whitespace. Is it because the lexer considers =>! an operator?

like image 292
Zhi Han Avatar asked Feb 16 '23 23:02

Zhi Han


1 Answers

You're right, it's unable to parse the first version correctly. Here are differences in the trees it generates for the first and second options:

scala> import scala.reflect.runtime.{universe => u}
import scala.reflect.runtime.{universe=>u}

scala> import scala.reflect.runtime.{currentMirror => m}
import scala.reflect.runtime.{currentMirror=>m}

scala> import scala.tools.reflect.ToolBox
import scala.tools.reflect.ToolBox

scala> val tb = m.mkToolBox()
tb: scala.tools.reflect.ToolBox[reflect.runtime.universe.type] = scala.tools.reflect.ToolBoxFactory$ToolBoxImpl@4426fc2e

scala> val treeNotWorking = tb.parse("(x:Boolean)=>!x")
treeNotWorking: tb.u.Tree = (x: Boolean).$eq$greater$bang(x)

scala> val treeWorking = tb.parse("(x:Boolean) => !x")
treeWorking: tb.u.Tree = ((x: Boolean) => x.unary_$bang)

As you can see, it tries to call the =>! on a boolean variable x defined elsewhere. For example, if we had x in the scope, we'd get a different error:

scala> val x = true
x: Boolean = true

scala> val a = (x:Boolean)=>!x
<console>:17: error: value =>! is not a member of Boolean
       val a = (x:Boolean)=>!x
like image 78
Alex Yarmula Avatar answered Feb 20 '23 09:02

Alex Yarmula