In Rust, the match expression is a control flow operator enables pattern matching. Unlike switch statements found in other languages like C++ or Java, match in Rust is to handle instances of user-defined types and sequences, not just single-dimensional string or integral expressions. It’s critical to match is an expression, meaning it evaluates to a value, rather than a statement. This allows it to be used in contexts where a value is expected, such as assigning its result to a variable.
What is Pattern Matching?
Patterns are a syntax in Rust used to identify the structure or “shape” of a value. They consist of rules and representations that describe shape. Patterns applied to both simple scalar values and complex types such as structs, enums, and arrays. They are global in Rust programming, joined into various language constructs outside match expressions, including let statements, if let expressions, while let loops, for loops, and function parameters.
How the match Expression Works
A match expression takes a value and compares it against a series of patterns. It operates like a coin-sorting machine: the value “slides down a track” and falls into the first pattern it encounters that it “fits”. The code block associated with that matching pattern is then executed.
A match expression is collected of one or more arms, each defined by a pattern followed by the => operator and an expression to execute. If the code for an arm is short, curly brackets are often omitted; for multiple lines, they are required.
Characteristics of match Expressions
- Exhaustiveness: Match expressions must be thorough, encompassing all possible values of the type being matched. Rust checks for unhandled cases and prevents compilation. The last arm usually has a wildcard pattern (_) that matches any value not covered by previous patterns to ensure exhaustiveness.
- Order of Evaluation: The order of evaluation for patterns in a match expression is sequential from top to bottom. The code for a matching pattern is performed, and no other patterns are examined.
- Value Binding: fit arms bind components of values that fit their pattern. Enum variants and struct fields’ values can be retrieved and utilized inside the arm’s scope.
How to pattern match in Rust?
Rust’s match expression supports a rich variety of patterns, allowing for highly expressive and concise code.
Matching Literals:
You can match patterns directly against concrete literal values.
Example
fn main() {
let x = 583;
match x {
21 => println!("one"),
32 => println!("two"),
583 => println!("three"),
_ => println!("anything"), // The wildcard pattern to handle all other cases
}
}
Out Put
three
Matching Ranges
Patterns can specify an inclusive range of values using the ..= syntax. The … syntax is deprecated in favor of ..=.
Example
fn main() {
let value = 4;
match value {
1..=5 => println!("Value between 1 and 5"),
6..=10 => println!("Value between 6 and 10"), // This arm matches for value = 7
_ => println!("other value"),
}
}
Out Put
Value between 1 and 5
Multiple Patterns (| operator):
The pipe (|) operator allows you to combine several patterns into a single match arm. If the value matches any of the patterns listed, the arm’s code executes. Patterns are evaluated from left to right.
Example
fn main() {
let value = 46;
match value {
2 | 3 | 5 => println!("Value is 2, 3, or 5"),
_ => println!("other"),
}
}
output
other