RFC-010b: Полнота сопоставления с образцом (деконструкция вариантов и исчерпываемость)
Настоящий документ является под-RFC для RFC-010 (унифицированный синтаксис типов). Объявление вариантов, форма вызова конструкции и представление tagged union во время выполнения (включая порядок объявления
variant_id— входной набор вариантов для проверки исчерпываемости в данном RFC) определены в разделе RFC-010 «Конструкция вариантов для типов в форме записи и sum type (авторитетное определение)»; настоящий RFC реализует зеркальную сторону: деконструкцию match и проверку исчерпываемости. Конструкция и деконструкция должны быть парными, поэтому они отнесены к одному RFC-010.Исходный номер RFC-039 (составлен 2026-09-03); 2026-09-25 по решению владельца объединён в под-RFC RFC-010 и перенумерован в RFC-010b, отслеживающий issue остаётся #330.
Резюме
Расширение сопоставления с образцом в match с текущего «только литералы + подстановочный знак» до полных возможностей: шаблоны вариантов Union (включая привязку полезной нагрузки), шаблоны структур/кортежей, реализация в IR шаблонов Or и охранных выражений, а также проверка исчерпываемости (E1030/E1031 переходят от пустого зарезервированного кода к реальной эмиссии). Данный RFC является предварительным условием для направления развития Error { kind: ErrorKind, message } (раздел развития в RFC-013 «Согласованность значений ошибок и сквозных кодов во время выполнения»), но мотивация самостоятельна — сопоставление с образцом представляет собой общую возможность языка, обслуживающую все типы с вариантами.
Мотивация
Текущее состояние — эмпирические данные (2026-09-03, код v0.7.12)
- На уровне IR реально реализованы только шаблоны литералов. AST уже определяет полный набор шаблонов (
src/frontend/core/parser/ast.rs:578: Wildcard / Identifier / Literal / Tuple / Struct / Union / Or / Guard), парсер способен разбирать шаблоны вариантов видаok(v),err(e)(Pattern::Union); однако генерация IR (начиная сsrc/middle/core/ir_gen.rs:5330) реализует только веткуLiteral, остальные шаблоны попадают в заглушку — загружается константа 0 для участия в сравнении на равенство, что никогда не приводит к совпадению; при этом если scrutinee в точности равен 0, происходит ошибочное совпадение с веткой-заглушкой (потенциально некорректное поведение). - Пример
match ok(v)/err(e)в stdlib.md — бумажная возможность. Синтаксис деконструкции вариантов, приведённый в документе спецификации (§1.3 Result), фактически не работает; реализация оператора?не проходит через десахаризацию match, что маскирует это обстоятельство. В тестовом корпусе нет ни одного случая деконструкции вариантов (match.yx/pattern_matching.yxпокрывают только литералы и подстановочный знак). - Проверка исчерпываемости висит в воздухе. E1030 (Pattern non-exhaustive), E1031 (Unreachable pattern) зарегистрированы в таблице кодов, но не имеют точек эмиссии — семантика match не определена.
- Развитие обработки ошибок заблокировано. Значение
Errorво время выполнения в настоящее время использует строковые коды{code, message}в качестве единственного программируемого контракта для различения (RFC-013); структурированное моделирование (match e.kind { file_not_found(path) => ... }) зависит от деконструкции вариантов и привязки полезной нагрузки из данного RFC.
Цели проектирования
- Деконструкция вариантов пригодна к использованию: деконструкция
match r { ok(v) => ..., err(e) => ... }и пользовательских наборов вариантов (sum type в стиле записи) семантически согласована по трём путям выполнения. - Исчерпываемость надёжна: E1030/E1031 эмитируются реально, пропуск ветки в match является ошибкой компиляции.
- Заглушки удалены: исключение поведения-заполнителя «загрузка 0 никогда не совпадает / совпадает ошибочно»; неподдерживаемые шаблоны должны порождать ошибку на этапе компиляции, а не молча приводить к неверному выполнению.
Предложение (уровень каркаса, подлежит наполнению)
| Возможность | Описание |
|---|---|
| Шаблоны вариантов Union | VariantName / VariantName(binding) — совпадение + привязка полезной нагрузки в область видимости ветки |
| Шаблоны Struct / Tuple | Реализация шаблонов полей и кортежей (AST уже имеется, IR дополняется) |
| Шаблон Or и Guard | Порядок вычисления и правила привязки для p1 | p2 и p if cond |
| Проверка исчерпываемости | E1030 — пропуск ветки, E1031 — недостижимость, область покрывает набор вариантов (Result/Option в настоящее время относятся к core; проверка не зависит от принадлежности, см. RFC-011b этап 2 — перенос в std) |
| Уточнение семантики шаблона Identifier | Необходимо определиться: голый идентификатор в текущем синтаксисе — это привязка или сравнение вариантов (связь с подстановочным знаком _) |
Открытые вопросы
- [ ] Шаблон Identifier: привязка новой переменной или сопоставление с существующим значением? (Семантика Rust vs сложившееся поведение в корпусе YaoXiang)
- [ ] Границы применимости исчерпываемости: как наборы вариантов, возвращаемые динамическим импортом или методами интерфейса, участвуют в проверке исчерпываемости?
- [ ] Нужен ли атрибут уровня
non_exhaustive(влияет на радиус разрушения расширений наборов вариантов std для пользовательских match)? - [ ] Должна ли ошибка компиляции предшествовать переходному периоду перед исправлением ошибочного совпадения заглушки при загрузке 0?
Связанные документы
- Раздел развития в RFC-013 «Согласованность значений ошибок и сквозных кодов во время выполнения» (
Error { kind, message }зависит от данного RFC) - RFC-036 модель тестирования (синтаксис сопоставления при проверке утверждений для ветвей ошибок)
- Закрытые случаи неприменимы; данный RFC представляет собой дополнение возможностей, а не исправление дефекта
