Scala match/case FAQ: Why am I getting an "unreachable code due to variable pattern" warning on my match/case statement when compiling my Scala code?
Reason for the error message
The usual reason for getting this error message is that you try to use an existing variable name inside a Scala match expression. For instance, if you try to create a match expression like this:
val x = 1 1 match { case x => println("x") // intentional error case _ => println("default match") }
you'll get this warning message when you try to compile the code:
$ scalac Test2.scala Test2.scala:7: warning: patterns after a variable pattern cannot match (SLS 8.1.1) If you intended to match against value x in object Test2, you must use backticks, like: case `x` => case x => println("x") ^ Test2.scala:8: warning: unreachable code due to variable pattern 'x' on line 7 case _ => println("default match") ^ two warnings found
Using a variable inside a match expression
Although your intent is to match the variable x
inside your match expression, and the code certainly looks correct to a newbie, the problem is with how Scala treats variable names inside a match expression like this.
Really, the problem is that match expressions have much more power than this simple example. With Scala match expressions you use something called variable patterns. For instance, the following example shows variable patterns for a String and an Int:
a match { case s: String => println(s) case i: Int => println(i) case _ => println("something else") }
In this example, s
and i
are used as variable names to match a String and an Int, and these are technically known as variable patterns. In this use, the variables s
and i
are created if a String or Int is matched, respectively.
For instance, if the match expression is given a String, then that pattern is matched, and Scala assigns the variable s
to the object the match expression was given. If it's given an Int, the other pattern matches, and the variable i
is assigned to the object. (If the match expression is given anything else, no match will be found, and the default case given by the _
will be triggered.) To be clear, s
and i
do not exist as variable names outside the match expression.
Conversely, the x
in the previous example is a constant that has been created outside the match expression.
The book "Programming in Scala" describes the situation like this:
"Scala uses a simple lexical rule for disambiguation: a simple name starting with a lowercase letter is taken to be a pattern variable; all other references are taken to be constants."
Solutions
There are a few possible solutions to this problem. The most obvious/normal solution in Scala is to use backticks around the variable name x
inside the match expression, like this:
val x = 1 1 match { case `x` => println("x") case _ => println("default match") }
Another solution is to change the lowercase x
to an uppercase X
, like this:
val X = 1 1 match { case X => println("x") case _ => println("default match") }
Either of those two approaches will work, but because I want to stay with the standard of having my variable names start with lowercase letters, I use the backticks solution.
Summary
I hope this explanation about the "unreachable code due to variable pattern" warning/error message has been helpful.