Комбинаторы парсеров для грамматики
Задача по программированию с проверкой онлайн
- Сложность
- Сложная
- Языки
- Python
- JavaScript
- TypeScript
- Java
- Go
- Темы
- Функции и замыкания
- Разбор и проверка данных
- Рекурсия и перебор
Грамматика задана списком правил rules, каждое — слова через пробел ИМЯ = ВИД АРГ…. Каждое правило — это парсер: получив строку и позицию, он либо успешно разбирает кусок от этой позиции и возвращает позицию после него, либо терпит неудачу. Виды:
lit T— ровно текстT(без пробелов, непустой);char C— один символ, входящий в строкуC;seq R1 R2 …— правила по очереди, каждое с того места, где закончилось предыдущее; неудача любого — неудача всего;alt R1 R2 …— упорядоченный выбор: результат первого успешного правила; к остальным вариантам после успеха не возвращаются, даже если дальше разбор не удастся;many R—Rноль или больше раз, жадно, покаRуспешно и продвигается вперёд; всегда успешно;opt R—R, а при неудаче — успех без продвижения;not R— успех без продвижения, еслиRтерпит неудачу, иначе неудача;sep R S— один или большеRчерез разделительS: после первогоRповторяет пару «S, затемR», пока пара успешна и продвигается вперёд; неудачная пара не съедает ничего. Аргументы видовseq…sep— имена правил (правило может ссылаться на объявленное позже и на себя, но левой рекурсии нет).
Для каждой строки inputs разберите её правилом start с позиции 0 и верните длину разобранного начала строки или -1 при неудаче. Строку целиком разбирать не нужно. До 30 правил, строки до 50 символов.
Пример: правила ["s = sep a b", "a = lit x", "b = lit -"], "s", ["x-x-", "-x"] → [3, -1].
Источник: задача CodeShare
Решить онлайнБесплатно и без регистрации: пишете код в браузере и проверяете его тестами (без аккаунта — несколько задач в день).