В языке программирования Rust, match является мощной конструкцией, которая позволяет сравнивать значение с серией шаблонов и выполнять код в зависимости от совпадения. Рассмотрим различные виды и применения match.
Конструкция match умеет значительно больше, чем простое сравнение числа с литералами. Она умеет деструктурировать сложные типы данных и уточнять шаблоны с помощью дополнительных условий — Match Guards.
Давайте разберём основные приёмы на интерактивном слайде:
Основы match: синтаксис, деструктуризация, Match Guards
Шаг 1/3
1fnmain(){ 2letseason="лето"; 3 4matchseason{ 5"весна"=>println!("Весна — всё цветёт"), 6"лето"=>println!("Лето — самое тёплое время"), 7"осень"=>println!("Осень — время листопада"), 8"зима"=>println!("Зима — время снега"), 9_=>println!("Неизвестное время года"),10}11}
Базовый синтаксис match
Конструкция match сравнивает значение с каждой «веткой» по порядку и выполняет код первого совпадения.
Паттерн _ — специальный «заглушитель», который срабатывает, если ни один другой шаблон не совпал. Rust требует, чтобы все возможные значения были обработаны.
Результат выполнения:
1fnmain(){2letpair=(0,-2);34matchpair{5(first,second)iffirst==0=>println!("Первый — 0, второй: {}",second),6(first,second)ifsecond==0=>println!("Первый: {}, второй — 0",first),7_=>println!("Другая комбинация"),8}9}
Match с деструктуризацией кортежей
match умеет разбирать (деструктурировать) сложные типы данных, например кортежи.
Здесь (first, second) if first == 0 совпадает с любым кортежем, где первый элемент равен 0, и связывает оба элемента с переменными.
Результат выполнения:
1fnmain(){ 2letpair=(4,7); 3 4matchpair{ 5(x,y)ifx==y=>println!("Числа одинаковые: {} и {}",x,y), 6(x,y)ifx+y==0=>println!("{} и {} — противоположны (сумма = 0)",x,y), 7(x,_)ifx%2==0=>println!("Первое число {} — чётное",x), 8_=>println!("Нет особой связи"), 9}10}
Match с условиями (Match Guards)
После шаблона можно дополнительно указать условие с помощью ключевого слова if.
Ветка срабатывает только если шаблон совпал и условие выполняется.
Это позволяет точно и лаконично фильтровать конкретные сценарии.
match особенно мощен в работе с перечислениями. Варианты enum могут не только быть простыми маркерами, но и хранить данные — и match позволяет их безопасно извлечь прямо в ветке шаблона.
match — основной инструмент для работы с перечислениями (enum) в Rust.
Каждая ветка соответствует одному из вариантов enum. Компилятор проверяет, что все варианты обработаны.
Вариант Color::RGB(r, g, b) извлекает (деструктурирует) числа из данных, хранящихся внутри этого варианта enum.
Результат выполнения:
1// ?hidden:start
2#[allow(dead_code)] 3// ?hidden:end
4enumExercise{ 5Run{distance: f64}, 6Swim{duration: u32}, 7Yoga, 8} 910fnprocess_exercise(exercise: Exercise){11matchexercise{12Exercise::Run{distance}=>{13println!("Ты пробежал {} км. Отлично!",distance);14}15Exercise::Swim{duration}=>{16println!("Ты плавал {} минут. Продолжай в том же духе!",duration);17}18Exercise::Yoga=>{19println!("Отличная работа — норма йоги на сегодня выполнена!");20}21}22}2324fnmain(){25process_exercise(Exercise::Run{distance: 10.5});26process_exercise(Exercise::Swim{duration: 45});27process_exercise(Exercise::Yoga);28}
Match с богатыми данными внутри Enum
Варианты enum могут хранить именованные поля (как в структуре).
В шаблоне Exercise::Run { distance } мы одновременно проверяем вариант и извлекаем поле distance.
Это позволяет безопасно и элегантно обработать разные «формы» одного типа.
Результат выполнения:
Шаблоны match позволяют обрабатывать различные варианты и извлекать связанные данные — безопасно и эффективно. Это даёт нам возможность легко обрабатывать различные случаи и извлекать данные из сложных типов, сохраняя при этом чистоту и ясность кода.
Когда мы используем match, мы не только упрощаем наш код, но и делаем его более надёжным. Компилятор гарантирует, что мы обработали все возможные варианты — иначе код просто не скомпилируется.
match в Rust — это мощный инструмент, который делает код более ясным и безопасным. Он позволяет обрабатывать различные случаи и извлекать данные из сложных типов в удобной и безопасной манере.
Также приятно отметить, что механизм паттерн-матчинга появился начиная с версии 3 в Dart (там используется ключевое слово switch) и активно применяется в языке Elixir.