Scala at Light Speed, Part 4: Pattern Matching
Learn Scala at light speed!
Join the DZone community and get the full member experience.
Join For FreeThis article series is for busy programmers who want to learn Scala fast, in 2 hours or less. The articles are the written version of Rock the JVM's Scala at Light Speed mini-course, which you can find for free on YouTube or on the Rock the JVM website in video form.
This is the third article of the series, which will focus on Scala as a functional programming language. You can watch it in video form here or in the embedded video below.
So far, we've covered:
- How to get started with Scala
- The very basics: values, expressions, types
- Object orientation: classes, instances, singletons, methods and basic generics
- Functional programming
You may also like: Scala at the Speed of Light, Part 1: The Essentials, Part 2: Object Orientation, and Part 3: Functional Programming
Enter Pattern Matching
Pattern matching is one of Scala's most powerful features. We'll start by analogy to other programming languages, where you've likely seen a switch statement. A pattern match is like a switch on steroids:
xxxxxxxxxx
val anInteger = 55
val order = anInteger match {
case 1 => "first"
case 2 => "second"
case 3 => "third"
case _ => anInteger + "th"
}
Much like anything else in Scala, a pattern matching structure is an expression, because it reduces to a value (one of the case values on the right-hand side of =>
). As a side note, the compiler is able to infer the type of the expression by inspecting the types returned by all cases (in this case String).
A few things about pattern matching:
- The underscore stands for anything (wildcard)
- The patterns are tested in order; the first one that matches will dictate the value of the expression.
- If no patterns match, a
MatchError
will be thrown.
More Than Just a Switch
Pattern matching can not only test for values, but for the structure of data, and can bind pieces of that data to names which can be used in the returned expression. The classic example is with case classes (which we mentioned in Part 2 are easily decomposable with pattern matching).
xxxxxxxxxx
// Case class decomposition
case class Person(name: String, age: Int)
val bob = Person("Bob", 43) // Person.apply("Bob", 43)
val personGreeting = bob match {
case Person(n, a) => s"Hi, my name is $n and I am $a years old."
case _ => "Something else"
}
In this PM expression, we're not testing bob
against a definitive value, but we're matching it against the Person structure, and in the case it does match, we're binding its fields to the names n
and a
so we can use them in the returned expression (notice the s-interpolated string).
PMs can match case classes and this kind of structures at a deep level, so if a case class contains a member that's another case class, you can match nested case classes with no problems.
Decomposing Other Structures
Some of the often used examples of PM decomposition include deconstructing tuples and lists. Let's see some code:
xxxxxxxxxx
// deconstructing tuples
val aTuple = ("Bon Jovi", "Rock")
val bandDescription = aTuple match {
case (band, genre) => s"$band belongs to the genre $genre"
case _ => "I don't know what you're talking about"
}
Much like case classes, we're matching against the tuple structure, and in the case, it matches; we're binding the members of the tuple to the respective names.
The truly magical feature is decomposing other structures, like lists:
xxxxxxxxxx
// decomposing lists
val aList = List(1,2,3)
val listDescription = aList match {
case List(first, 2, _) => s"List with 2 on its second position, starting with $first"
case _ => "unknown list"
}
The PM case says: try to match aList
to the structure of a list containing exactly 3 elements; the first can be anything and will be named first
, the second must be exactly 2, and the third is unimportant.
There are lots of other patterns and capabilities to the PM feature in Scala, but we will keep this short for now so that we don't needlessly overcomplicate things.
In the next article in the series, we will go through some of the advanced Scala features that you will likely see in real-life code. Stay tuned!
Further Reading
Opinions expressed by DZone contributors are their own.
Trending
-
Implementing a Serverless DevOps Pipeline With AWS Lambda and CodePipeline
-
How To Use Pandas and Matplotlib To Perform EDA In Python
-
What Is JHipster?
-
4 Expert Tips for High Availability and Disaster Recovery of Your Cloud Deployment
Comments