#php #регулярные_выражения
Есть текст, типа: "Осталось 10 часов 15 минут 12 секунд". Некоторые компоненты (часы, минуты, секунды) могут отсутствовать. Нужно выдернуть циферки и соотнести с часами, минутами, секундами. Делаю так: Осталось\s+(?!(\d+)\s+(час).*?)(?!(\d+)\s+(минут).*?)(?!(\d+)\s+(секунд).*?) Текст подходит под регулярное выражение, но от него всегда остается только "Осталось " при любых комбинациях час., мин., сек. P.S. Нашел информацию по (?!...). Они, оказывается, используются только для проверки, но ничего не выводят. Каким образом можно одновременно проверить наличие фрагментов и выдернуть данные?
Ответы
Ответ 1
Нужно использовать комбинацию из проверяемой части и захватывающей части. Примерно вот так: Осталось\s+((?\d+)\s+час(а|ов)?\s*)?((? \d+)\s+минут(а|ы)?\s*)?((? \d+)\s+секунд(а|ы)?)? После обработки в именованных группах будут требуемые значения. Демо тут (спасибо за наводку @stribizhev) Ответ 2
Мне кажется, Вы путаете необязательные группы с блоками предварительного просмотра (look-ahead). Вместо (?!...) надо использовать (?:...)?, а окончания отлавливать с помощью \p{L}*: Осталось\s+(?:(\d+)\s+час\p{L}*)?(?:\s*(\d+)\s+минут\p{L}*)?(?:\s*(\d+)\s+секунд\p{L}*)? ^^ ^ Код: $re = '/Осталось\s+(?:(\d+)\s+час\p{L}*)?(?:\s*(\d+)\s+минут\p{L}*)?(?:\s*(\d+)\s+секунд\p{L}*)?/u'; См. демо
Комментариев нет:
Отправить комментарий