Scala Pattern Guards
A pattern guard is an if condition written after a pattern in a match case. It lets a case match only when its pattern and its condition both hold.
A guard picks the grade band
85 fails the 90 guard but passes the 80 guard. The second case gives the grade.
@main def main(): Unit =
val grade = 85 match
case n if n >= 90 => "A"
case n if n >= 80 => "B"
case _ => "C"
println(grade)A failed guard falls through
30 fails the passing guard. The catch-all case then gives the failing grade.
@main def main(): Unit =
val result = 30 match
case n if n >= 50 => "pass"
case _ => "fail"
println(result)A guard can test a bound name
The tuple pattern binds the name and the age. The guard tests the bound age.
@main def main(): Unit =
val pair = ("Ana", 17)
val result = pair match
case (name, age) if age >= 18 => name + " adult"
case (name, _) => name + " minor"
println(result)Example
def classify(n: Int): String = n match
case x if x < 10 => "small"
case x if x < 20 => "medium"
case _ => "large"
@main def main(): Unit =
println(List(5, 12, 20).map(classify))Key points
- Guard: an if test placed after a pattern, before the arrow.
- Use a guard for a range or a property that a plain pattern cannot express.
- When the guard is false, the match tries the next case, even for the same pattern shape.
- A guard can use a name bound by its own pattern.
- Put the most specific guarded case before a wider case for the same value.
In this example, classify uses two guards and a catch-all. Each number takes the first case whose guard holds. The mapped list shows one label per number, in order.
Note
a guard runs only after its pattern matches, so a failed pattern skips the guard.
Try it Yourself
Edit the code, then press Run.
Running is simulated · Scastie
Exercise
What does 7 match with case n if n > 10 => "big" and case _ => "small" give?