diff --git a/_tour/pattern-matching.md b/_tour/pattern-matching.md index a89c16775f..e2a3929010 100644 --- a/_tour/pattern-matching.md +++ b/_tour/pattern-matching.md @@ -138,6 +138,69 @@ println(showNotification(someVoiceRecording)) // prints You received a Voice Re The function `showNotification` takes as a parameter the abstract type `Notification` and matches on the type of `Notification` (i.e. it figures out whether it's an `Email`, `SMS`, or `VoiceRecording`). In the `case Email(sender, title, _)` the fields `sender` and `title` are used in the return value but the `body` field is ignored with `_`. +## Matching on string + +The `s`-interpolator allows embedding variables in strings and is also useful for pattern matching. + +{% tabs s-interpolator-pattern-matching class=tabs-scala-version %} +{% tab 'Scala 2' for=s-interpolator-pattern-matching %} +```scala +val input: String = "Alice is 25 years old" + +input match { + case s"$name is $age years old" => s"$name's age is $age" + case _ => "No match" +} +// Result: "Alice's age is 25" +``` +{% endtab %} +{% tab 'Scala 3' for=s-interpolator-pattern-matching %} +```scala +val input: String = "Alice is 25 years old" + +input match + case s"$name is $age years old" => s"$name's age is $age" + case _ => "No match" +// Result: "Alice's age is 25" +``` +{% endtab %} +{% endtabs %} + +In this example, name and age extract parts of the string based on the pattern. This is helpful for parsing structured text. + +We can also use extractor objects for string pattern matching. + +{% tabs s-interpolator-pattern-matching-2 class=tabs-scala-version %} +{% tab 'Scala 2' for=s-interpolator-pattern-matching-2 %} +```scala +object Age { + def unapply(s: String): Option[Int] = s.toIntOption +} + +val input: String = "Alice is 25 years old" + +val (name, age) = input match { + case s"$name is ${Age(age)} years old" => (name, age) +} +// name: String = Alice +// age: Int = 25 +``` +{% endtab %} +{% tab 'Scala 3' for=s-interpolator-pattern-matching-2 %} +```scala +object Age: + def unapply(s: String): Option[Int] = s.toIntOption + +val input: String = "Alice is 25 years old" + +val (name, age) = input match + case s"$name is ${Age(age)} years old" => (name, age) +// name: String = Alice +// age: Int = 25 +``` +{% endtab %} +{% endtabs %} + ## Pattern guards Pattern guards are boolean expressions which are used to make cases more specific. Just add `if ` after the pattern.