🔍
Инструменты разработчика
May 21, 20269 min readBy BrowseryTools

Регулярные выражения: полное руководство для разработчиков

Практическое руководство по регулярным выражениям: базовый синтаксис, группы захвата, lookahead/lookbehind, типичные паттерны и отладка в разных языках программирования.

регулярные выраженияregexразработкаJavaScriptPython

Регулярные выражения — это инструмент, который разработчики либо любят, либо избегают полностью. Они выглядят устрашающе — плотная строка специальных символов, кажущаяся непостижимой, — но базовая модель проста. Как только вы понимаете, как они работают, хорошо написанное регулярное выражение превращается в один из мощнейших однострочных инструментов во всём вашем арсенале.

Это руководство отсекает лишнее. Вместо перечисления всех возможностей регулярных выражений оно сосредоточено на 20% синтаксиса, покрывающего 80% реальных задач: классы символов, квантификаторы, якоря, группы и флаги. По ходу дела вы можете тестировать каждый пример в Тестере регулярных выражений BrowseryTools — бесплатно, без регистрации, всё остаётся в браузере.

Что такое регулярное выражение?

Регулярное выражение — это паттерн, описывающий множество строк. Применяя регулярное выражение к тексту, вы спрашиваете: «соответствует ли эта строка моему паттерну?» — или, на практике: «найди все подстроки, соответствующие моему паттерну». Сам паттерн записывается на компактном мини-языке, нативно поддерживаемом большинством языков программирования.

Регулярные выражения полезны всякий раз, когда нужно валидировать ввод (является ли это корректным email-адресом?), извлечь данные (выбрать все URL из блока текста), преобразовать текст (заменить все вхождения паттерна) или разбить строку по сложному разделителю. Они работают в браузере, на сервере, в терминале — везде.

Основной синтаксис: 20%, покрывающие 80% задач

Литеральные символы и точка

Большинство символов в регулярном выражении совпадают сами с собой. Паттерн hello буквально совпадает со строкой «hello». Точка . — единственный универсальный подстановочный символ, совпадающий с любым одним символом, кроме новой строки. Так, h.llo совпадает с «hello», «hallo», «hxllo» и так далее.

Классы символов

Квадратные скобки определяют класс символов — набор, из которого в данной позиции может совпасть любой один символ.

  • [aeiou] — совпадает с любой гласной
  • [a-z] — совпадает с любой строчной буквой (синтаксис диапазона)
  • [A-Za-z0-9] — совпадает с любым буквенно-цифровым символом
  • [^0-9]^ внутри скобок инвертирует класс; совпадает с чем угодно, кроме цифры

Сокращённые классы охватывают наиболее распространённые случаи: \d — любая цифра (то же, что [0-9]), \w — любой «словесный» символ (буквы, цифры, подчёркивание), \s — любой пробельный символ. Их заглавные обратные — \D, \W, \S — совпадают с противоположным.

Квантификаторы

Квантификаторы управляют количеством повторений предшествующего элемента.

  • * — ноль или более раз
  • + — один или более раз
  • ? — ноль или один раз (делает элемент необязательным)
  • {3} — ровно 3 раза
  • {2,5} — от 2 до 5 раз включительно
  • {3,} — 3 или более раз

По умолчанию квантификаторы жадные — они захватывают как можно больше. Добавление ? после квантификатора делает его ленивым: .*? захватывает как можно меньше. Это различие важно при извлечении контента между разделителями.

Якоря

Якоря не совпадают с символами; они совпадают с позициями в строке.

  • ^ — начало строки (или начало строки в многострочном режиме)
  • $ — конец строки (или конец строки в многострочном режиме)
  • \b — граница слова — позиция между словесным и несловесным символом

Якоря необходимы для валидации. Без них паттерн \d+ совпал бы с цифрами внутри «abc123xyz». С якорями — ^\d+$ — он совпадает только со строками, состоящими исключительно из цифр.

Группы и чередование

Скобки создают захватывающие группы. Они служат двум целям: группировке подвыражения для применения квантификатора ко всей группе и захвату совпавшей подстроки для извлечения.

// Group with quantifier: match one or more "ab" repetitions
/(ab)+/   →  matches "ab", "abab", "ababab"

// Alternation with |: match "cat" or "dog"
/(cat|dog)/  →  matches "I have a cat" and "I have a dog"

// Named capture group
/(?<year>d{4})-(?<month>d{2})-(?<day>d{2})/

Незахватывающие группы — (?:...) — группируют без захвата, что чище, когда нужна только группировка без извлечения совпавшего текста.

Практические примеры

Валидация email

/^[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+.[a-zA-Z]{2,}$/

Разбор: ^ привязывает к началу. [a-zA-Z0-9._%+-]+ совпадает с локальной частью (один или более допустимых символов). @ — буквальный символ «@». [a-zA-Z0-9.-]+ совпадает с доменным именем. \. — буквальная точка (экранированная, так как неэкранированная . означает «любой символ»). [a-zA-Z]{2,} совпадает с доменом верхнего уровня длиной не менее 2 букв. $ привязывает к концу.

Номер телефона (формат США)

/^+?1?s?((?d{3})?[s.-]?)(d{3}[s.-]?d{4})$/

Совпадает с форматами вроде 555-867-5309, (555) 867-5309, +1 555 867 5309 и 5558675309. Ключевой приём — использование ? для необязательных разделителей и группировки кода города с необязательными скобками.

Извлечение URL из текста

/https?://[^s"'<>]+/g

https? совпадает с «http» и «https» (символ s необязателен). :\/\/ совпадает с буквальным «://» с экранированными косыми чертами. [^\s"'<>]+ совпадает со всем, что не является пробелом или типичными завершающими символами URL. Флаг g находит все совпадения, а не только первое.

Флаги регулярных выражений

Флаги изменяют применение всего паттерна.

  • g (глобальный) — находит все совпадения, а не только первое
  • i (без учёта регистра) — рассматривает верхний и нижний регистр как эквивалентные; /hello/i совпадает с «Hello», «HELLO» и «hello»
  • m (многострочный) — заставляет ^ и $ совпадать с началом/концом каждой строки, а не всей строки целиком
  • s (dotAll) — заставляет . также совпадать с символами новой строки, полезно для совпадения через разрывы строк

В JavaScript флаги идут после закрывающей косой черты: /pattern/gi. В Python они передаются вторым аргументом: re.findall(pattern, text, re.IGNORECASE).

JavaScript vs Python: ключевые различия

Синтаксис регулярных выражений в основном одинаков в JavaScript и Python, но есть несколько важных отличий.

  • Именованные группы: JavaScript использует (?<name>...), Python — то же самое. Обе возвращают именованные группы, но доступ к ним различается — match.groups.name в JS, match.group('name') в Python.
  • Просмотр вперёд/назад: обе поддерживают (?=...) (положительный просмотр вперёд) и (?!...) (отрицательный). Python также поддерживает просмотры назад переменной длины; более старые движки JavaScript — нет.
  • Unicode: JavaScript требует флага u для обработки экранирований свойств Unicode вроде \p{Letter}. Модуль re в Python обрабатывает Unicode по умолчанию.
  • Сырые строки: в Python всегда используйте сырые строки (r"\d+"), чтобы избежать двойного экранирования. В JavaScript используйте либо литеральный синтаксис /\d+/, либо строку "\\d+" при конструировании через new RegExp().

Типичные ошибки в регулярных выражениях

  • Катастрофический откат — паттерны вроде (a+)+ на несовпадающей строке могут вызвать экспоненциальный откат, блокируя движок. Избегайте вложенных квантификаторов для перекрывающихся паттернов.
  • Забытое экранирование точки3.14 как паттерн совпадает с «3X14», потому что . — подстановочный символ. Используйте 3\.14 для совпадения с буквальной точкой.
  • Отсутствие якорей в паттернах валидации — без ^ и $ паттерн, предназначенный для валидации всей строки, совпадёт с любой строкой, содержащей паттерн как подстроку.
  • Использование регулярных выражений для разбора HTML — регулярные выражения не могут обрабатывать произвольно вложенные структуры. Используйте настоящий HTML-парсер (DOMParser в браузере, BeautifulSoup в Python) для разбора HTML.

Тестируйте паттерны безопасно в браузере

Писать регулярные выражения в редакторе без обратной связи — мучение. Написали паттерн, запустили код, увидели ошибку, поправили паттерн, запустили снова. Живой тестер регулярных выражений замыкает этот цикл — вы видите совпадения, подсвеченные в реальном времени по мере ввода.

Тестер регулярных выражений BrowseryTools позволяет написать паттерн, вставить тестовые строки и мгновенно увидеть все совпадения подсвеченными. Он работает полностью в браузере, так что вы можете тестировать на реальных данных — логах, пользовательском вводе, production-строках — без отправки чего-либо на сервер.

Итоги

Регулярные выражения окупают вложенное в их изучение время. Базовый словарь — классы символов, квантификаторы, якоря, группы и флаги — невелик. Паттерны, которые можно на его основе строить, — безграничны. Начните с примеров из этого руководства, тестируйте их на собственных строках, и синтаксис станет интуитивным быстрее, чем вы ожидаете.


🛠️

Try the Tools — 100% Free, No Sign-Up

Everything runs in your browser. No uploads. No accounts. No ads.

Explore All Tools →