Регулярные выражения в JavaScript — это компактный язык шаблонов для поиска, проверки, извлечения и замены фрагментов текста. Если объяснить проще, regexp работает как очень точный фильтр: он не «понимает» смысл текста как человек, зато блестяще распознаёт форму — цифры, даты, пробелы, домены, коды, артикулы, повторяющиеся символы и тысячи других текстовых конструкций, которые в прикладной разработке встречаются ежедневно.
Что такое регулярные выражения в JavaScript
Регулярное выражение — это шаблон, по которому движок JavaScript сопоставляет строки и находит в них нужные последовательности символов. На практике это означает, что вместо десятков условий с проверкой каждого символа можно описать правило одной компактной конструкцией.
В JavaScript регулярные выражения создаются двумя основными способами:
- Через литерал: удобно, когда шаблон известен заранее.
- Через конструктор
RegExp: подходит, когда шаблон собирается динамически.
const re1 = /hello/i;
const re2 = new RegExp('hello', 'i');
Здесь флаг i означает нечувствительность к регистру. То есть шаблон найдёт и Hello, и HELLO, и hello.
У регулярных выражений в JavaScript несколько типовых сценариев применения:
- валидация ввода в формах;
- поиск данных в логах и сообщениях;
- очистка строк;
- разделение текста на фрагменты;
- замена по шаблону;
- извлечение данных из URL, email, телефонов, кодов заказов.
Если представить строку как железнодорожную линию, то regexp — это контролёр с очень точным маршрутом. Он знает, где начинается путь, через какие «остановки» должен пройти шаблон, какие символы можно пропустить, а какие обязательны, и где именно проверка заканчивается. Например, у шаблона /^\d{4}-\d{2}-\d{2}$/ маршрут начинается строго в начале строки, затем останавливается на четырёх цифрах, потом на дефисе, потом на двух цифрах, ещё раз на дефисе, затем на двух цифрах и заканчивается строго в конце строки. Никаких лишних остановок, отклонений и «посадок по пути».
Из чего состоят regexp: символы, классы, якоря и квантификаторы
Структура регулярного выражения — это набор специальных токенов, каждый из которых задаёт конкретное правило сопоставления. Понимание этих элементов даёт возможность читать и писать шаблоны без догадок.
Обычные символы
Если символ не имеет специального значения, он ищется буквально.
/cat/
Такой шаблон найдёт последовательность cat в строке my cat sleeps.
Метасимволы
Метасимволы — это служебные обозначения, которые управляют логикой поиска.
| Символ | Значение | Пример |
|---|---|---|
| . | любой символ, кроме перевода строки | /a.c/ |
| \d | любая цифра | /\d+/ |
| \w | буква, цифра или подчёркивание | /\w+/ |
| \s | пробельный символ | /\s/ |
| \D | не цифра | /\D+/ |
| \W | не буква, не цифра и не подчёркивание | /\W/ |
| \S | не пробельный символ | /\S+/ |
Классы символов
Класс символов — это перечисление допустимых символов в одной позиции. Он особенно полезен, когда вариантов немного и они заранее известны.
/[abc]/ // a или b или c
/[A-Z]/ // любая латинская заглавная буква
/[0-9]/ // любая цифра
Отрицание внутри квадратных скобок задаётся через ^:
/[^0-9]/
Это означает «любой символ, кроме цифры».
Якоря начала и конца строки
Якоря — это позиционные маркеры, которые не ищут символ сами по себе, а указывают, где именно шаблон должен сработать. Они особенно важны в валидации.
/^hello/ // строка должна начинаться с hello
/world$/ // строка должна заканчиваться на world
/^cat$/ // строка должна быть ровно cat
Вот здесь особенно полезно думать о маршруте буквально. У шаблона /^AB\d{6}Z$/ точный путь такой:
- Начало строки.
- Остановка 1: символ
A. - Остановка 2: символ
B. - Остановки 3–8: ровно шесть цифр.
- Остановка 9: символ
Z. - Конец строки.
Если хотя бы одна «остановка» пропущена, маршрут считается недействительным.
Квантификаторы
Квантификатор задаёт, сколько раз должен повторяться предыдущий элемент. Это один из самых мощных инструментов regexp.
| Квантификатор | Значение | Пример |
|---|---|---|
| * | 0 или более раз | /ab*/ |
| + | 1 или более раз | /ab+/ |
| ? | 0 или 1 раз | /colou?r/ |
| {3} | ровно 3 раза | /\d{3}/ |
| {2,5} | от 2 до 5 раз | /\w{2,5}/ |
Как использовать регулярные выражения в JavaScript на практике
Использование regexp в JavaScript строится вокруг стандартных методов строк и объектов RegExp, которые позволяют проверять наличие совпадения, извлекать данные и заменять текст. Фактически разработчик выбирает не «можно ли сделать regex», а «какой именно метод лучше соответствует задаче».
Метод test()
test() возвращает true или false, если совпадение найдено или не найдено.
/\d/.test('Order 42'); // true
Это лучший выбор для валидации формата.
Метод match()
match() извлекает совпадения из строки.
'Price: 199 USD'.match(/\d+/);
Метод replace()
replace() заменяет найденные фрагменты на новый текст.
'2025/05/26'.replace(/\//g, '-');
Метод search()
search() возвращает индекс первого совпадения или -1.
'user@example.com'.search(/@/);
Метод split()
split() делит строку по шаблону, а не только по фиксированному символу.
'apple, orange;banana'.split(/[;,]\s*/);
Я часто советую начинающим сначала формулировать задачу словами, а уже потом превращать её в regexp. Если сразу писать шаблон, мозг цепляется за символы и легко пропустить логику: где начало, где конец, какие элементы обязательны, а какие допустимы как опция.
Регулярных выражений в JavaScript: базовые шаблоны для реальных задач
Базовые шаблоны — это готовые конструкции для типовых сценариев, которые экономят время и уменьшают число ошибок при работе со строками. Однако каждый такой шаблон нужно проверять на границы применимости, потому что «похоже на рабочее» и «действительно корректно» — не одно и то же.
Проверка целого числа
/^\d+$/
Маршрут проверки:
- Начало строки.
- Одна или более цифр.
- Конец строки.
Подходящие строки: 7, 2025, 0001. Неподходящие: 12a, 45, 4.2.
Проверка даты в формате YYYY-MM-DD
/^\d{4}-\d{2}-\d{2}$/
Этот шаблон проверяет именно форму записи, а не реальность календарной даты. Строка 2025-13-99 по форме подходит, но логически неверна. Поэтому для дат лучше сочетать regexp с дополнительной проверкой через объект Date.
Извлечение всех чисел из текста
const result = 'ID: 52, room 804'.match(/\d+/g);
Флаг g включает глобальный поиск — то есть находит не одно совпадение, а все.
Удаление лишних пробелов
const cleaned = text.replace(/\s+/g, ' ').trim();
Это частый приём при нормализации пользовательского ввода.
Простейшая проверка email
/^[^\s@]+@[^\s@]+\.[^\s@]+$/
Такой шаблон полезен для быстрой интерфейсной проверки, но не покрывает все допустимые адреса по стандартам RFC. По данным Internet Message Format RFC 5322 и более поздних спецификаций, формат email может быть гораздо сложнее, чем принято в бытовых примерах. Поэтому в production-валидации лучше комбинировать regex, подтверждение почты и серверную проверку.
Флаги regexp: как меняется поведение поиска
Флаги — это модификаторы, которые задают режим работы регулярного выражения и напрямую влияют на результат поиска. Один и тот же шаблон без флагов и с флагами может вести себя как два разных инструмента.
| Флаг | Назначение | Пример |
|---|---|---|
| g | искать все совпадения | /\d/g |
| i | игнорировать регистр | /hello/i |
| m | многострочный режим для ^ и $ | /^item/m |
| s | точка захватывает перевод строки | /a.b/s |
| u | корректная работа с Unicode | /\p{L}/u |
| y | липкий поиск с текущей позиции | /\d/y |
Особенно важен флаг u. Без него работа с некоторыми символами Unicode может быть некорректной. Это практически значимо в проектах с многоязычным интерфейсом, эмодзи, именами пользователей и текстами, содержащими расширенные наборы символов.
Группы, альтернативы и захват подстрок
Группы — это способ объединять части шаблона, извлекать фрагменты текста и применять правила повторения к целым блокам. Они делают регулярные выражения не просто фильтром, а инструментом структурного разбора строки.
Обычные группы
/(\d{4})-(\d{2})-(\d{2})/
Здесь отдельно захватываются год, месяц и день.
const m = '2025-05-26'.match(/(\d{4})-(\d{2})-(\d{2})/);
// m[1] = 2025
// m[2] = 05
// m[3] = 26
Незахватывающие группы
/(?:https?:\/\/)?example\.com/
Конструкция (?:...) группирует выражение без сохранения подмаски в результирующем массиве.
Альтернатива
/cat|dog|bird/
Шаблон найдёт один из перечисленных вариантов.
Именованные группы
const re = /(?<year>\d{4})-(?<month>\d{2})-(?<day>\d{2})/;
Именованные группы заметно повышают читаемость там, где шаблон используется долго и поддерживается несколькими разработчиками.
С практической точки зрения люди чаще ошибаются не в синтаксисе групп, а в том, что забывают про жадность шаблона. Психологически это объяснимо: человек склонен читать шаблон слева направо как инструкцию, а движок regexp ещё и применяет внутренние правила выбора совпадения. В итоге кажется, что выражение «должно было взять меньше», но оно берёт больше, потому что квантификатор жадный.
Жадные и ленивые квантификаторы: где чаще всего ошибаются
Жадный квантификатор пытается захватить максимально возможный фрагмент, а ленивый — минимально достаточный для совпадения. Эта разница критична при парсинге HTML-подобных строк, кавычек, скобок и повторяющихся блоков.
/<div>.*<\/div>/
Такой шаблон может захватить слишком много.
/<div>.*?<\/div>/
А здесь *? делает поиск ленивым.
Практическое наблюдение: в формах, шаблонах писем и простом текстовом парсинге именно жадные квантификаторы создают наибольшее число «тихих» ошибок — не падение кода, а неверный результат. Разработчик видит, что match что-то нашёл, и не сразу замечает, что найденный фрагмент длиннее ожидаемого.
Когда я проверяю чужой код с regexp, первым делом смотрю на сочетания
.*и.+. В реальных задачах именно они чаще всего превращают аккуратный шаблон в пылесос, который засасывает лишний текст.
Какие ошибки при работе с regexp в JavaScript встречаются чаще всего
Типичные ошибки в regexp — это отсутствие якорей, избыточная жадность, неправильное экранирование и попытка решить регулярным выражением задачу, которая требует полноценного парсера. Проще говоря, regex силён в шаблонах, но не всемогущ.
1. Отсутствие якорей при валидации
/\d+/
Этот шаблон лишь находит цифры внутри строки, но не проверяет, что вся строка состоит только из цифр.
Правильно:
/^\d+$/
2. Неверное экранирование точки
/example.com/
Точка здесь означает любой символ. Поэтому шаблон совпадёт и с exampleXcom.
Правильно:
/example\.com/
3. Попытка одной regex-проверкой гарантировать корректность сложных данных
Например, формат даты, URL или email можно проверить по форме, но не всегда по логике и стандартам. URL регулируется RFC 3986, а email — несколькими RFC, и их полное покрытие одним шаблоном обычно неоправданно сложно.
4. Игнорирование Unicode
Современные интерфейсы давно вышли за пределы ASCII. Если строка содержит комбинированные символы, национальные алфавиты или эмодзи, шаблон без u может вести себя неожиданно.
Когда regexp подходит идеально, а когда лучше выбрать другой инструмент
Regexp идеально подходит для распознавания формализованных текстовых паттернов, но уступает специализированным парсерам там, где данные имеют вложенную структуру и зависят от контекста. Это базовый критерий выбора инструмента.
Регулярные выражения отлично подходят для:
- артикулов и кодов;
- простых проверок формата;
- очистки и нормализации текста;
- извлечения повторяющихся шаблонов;
- поиска по логам и журналам событий.
Лучше выбрать другой инструмент для:
- разбора сложного HTML и XML;
- анализа JSON;
- полной проверки URL по спецификации;
- сценариев, где важны вложенность и контекст.
Здесь полезна аналогия с кухонным ножом. Хороший нож универсален и решает множество задач, но им неудобно откручивать винты и измерять температуру. Точно так же regexp великолепен в текстовых шаблонах, но не должен подменять инструменты, созданные для структурного синтаксического разбора.
Мини-чеклист: как писать понятные и надёжные регулярные выражения
Надёжное регулярное выражение начинается с точной формулировки входного формата и заканчивается проверкой на реальных строках, включая пограничные случаи. Этот подход резко снижает число скрытых ошибок.
- Сначала опишите формат словами.
- Зафиксируйте начало и конец строки, если нужна валидация.
- Экранируйте специальные символы:
.,+,(,),[,]. - Избегайте
.*, если можно описать диапазон точнее. - Проверяйте шаблон на негативных примерах, а не только на позитивных.
- Используйте именованные группы в длинных выражениях.
- Для Unicode-текста включайте
u, когда это уместно. - Не пытайтесь regex-ом заменить полноценную бизнес-валидацию.
Согласно State of JS, JavaScript стабильно остаётся одной из самых используемых технологий среди веб-разработчиков, а значит работа со строками, пользовательским вводом, URL и данными форм остаётся повседневной практикой. В такой среде знание regexp — не абстрактный навык, а реальный инструмент экономии времени и снижения числа багов.
Регулярные выражения в JavaScript нужны там, где текст должен подчиняться чёткой форме: от чисел и дат до шаблонов адресов и кодов. Если понимать символы, якоря, квантификаторы, группы и флаги, regexp перестаёт выглядеть как «магическая строка» и превращается в предсказуемый рабочий инструмент. Главное — строить шаблон как точный маршрут с понятным началом, последовательными остановками и строгим концом, а не как набор символов на удачу.
