Регулярные выражения. Основы

  Владислав Титов  | 

  Обновл. 4 Окт 2019  | 

 1001

Регулярное выражение — это описание шаблона символов.

Вступление

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

Регулярное выражение: th
Пример: There is no theory of evolution. Only a list of animals Chuck Norris allows to live.

Вы можете быть удивлены, почему не было найдено совпадение в слове There. Дело в том, что это слово содержит заглавную букву T, а не строчную, как в искомом регулярном выражении. Мы знаем, что это один и тот же символ, просто в другой форме. Однако это не относится к регулярным выражениям. Регулярные выражения не определяют значения искомой последовательности. Всё, что они делают — это ищут точные совпадения с тем, что описывает шаблон.

Очень простое выражение, подобное этому, на самом деле ничем не отличается от поискового запроса, который вы можете выполнить в поисковой системе (Google/Яндекс) или в вашем любимом текстовом редакторе.

Метасимволы


Символ точки (.) является метасимволом. Метасимволы — это символы, которые имеют особое значение. Они помогают создавать более интересные шаблоны, чем просто набор конкретных символов. Практически всё, что мы будем рассматривать — будет метасимволами.

Точка (.) представляет собой любой символ. В следующем примере мы ищем символ b, за которым следует любой символ, а за ним символ g:

Регулярное выражение: b.g
Пример: The big bag of bits was bugged.

Важно отметить, что точка (.) соответствует только одному символу. Мы можем заставить её соответствовать более чем одному символу, используя множители, которые мы рассмотрим ниже. Кроме того, вы также можете искать несколько символов с помощью точки следующим образом:

Регулярное выражение: l..e
Пример: You can live like a king but make sure it isn't a lie.

В примере выше мы сопоставляем букву l, за которой следуют любые два символа, и за которыми следует e.

Диапазоны символов

Символ точки (.) позволяет нам установить соответствие любому символу. Но иногда нам необходимо быть более конкретными. В этом случае будут полезны диапазоны. Мы указываем диапазон символов, заключая их в квадратные скобки []:

Регулярное выражение: t[eo]d
Пример: When today is over Ted will have a tedious time tidying up.

В регулярном выражении выше мы ищем символ t, за которым следует либо символ e, либо o, и за которым следует символ d.

Количество символов, которые вы можете поместить в квадратные скобки, не ограничено. Вы можете разместить один символ, например, [у] (это было бы немного глупо, но, тем не менее, это не нарушает правила), или вы можете указать несколько символов, например, [Grf4s2 # lknx].

Короткая запись


Допустим, мы хотим найти наличие цифр от 1 до 8. Мы могли бы использовать для поиска следующий диапазон: [12345678], но есть вариант получше:

Регулярное выражение: [1-8]
Пример: Room Allocations: G4 G9 F2 H1 L0 K7 M9

Вы можете комбинировать набор символов вместе с другими символами:

Регулярное выражение: [1-49]
Пример: Room Allocations: G4 G9 F2 H1 L0 K7 M9

В регулярном выражении выше мы ищем цифры 1, 2, 3, 4 или 9.

Мы также можем объединить несколько наборов. В регулярном выражении ниже мы ищем 1, 2, 3, 4, 5, a, b, c, d, e, f, x:

Регулярное выражение: [1-5a-fx]
Пример: A random set of characters: y, w, a, r, f, 4, 9, 6, 3, p, x, t

Использование наборов символов иногда может привести к странному поведению. Например, вы можете использовать диапазон [a-f] и обнаружить, что ему соответствует символ D. Это связано с таблицами символов, которые использует система. В большинстве системах есть таблица символов, в которой сначала идут все строчные буквы, а затем заглавные (например, abcdef .... xyzABCD ...). Однако некоторые системы чередуют строчные и прописные буквы (например, aAbBcCdD ... yYzZ). Если вы столкнулись с каким-то странным поведением и, при этом, используете диапазоны, то это первое, что нужно проверять.

Поиск несоответствующих символов

Иногда нам может понадобиться найти символ, который не входит в диапазон искомых. Мы можем это сделать, поместив знак вставки (^) в начало диапазона:

Регулярное выражение: t[^eo]d
Пример: When today is over Ted will have a tedious time tidying up.

Совет: Любые символы, которые обычно имеют особое значение (метасимволы), теряют своё особое значение и становятся обычными символами, находясь внутри диапазона. Исключением является знак вставки (^), который приобретает новое значение — отрицание.

Мультипликаторы


Мультипликаторы позволяют увеличить количество раз, когда элемент может появиться в нашем регулярном выражении. Вот основной набор мультипликаторов:

   * — значение встречается 0 или более раз.

   + — значение встречается 1 или несколько раз.

   ? — значение встречается 0 или 1 раз.

   {5} — значение встречается 5 раз.

   {3,7} — значение встречается от 3 до 7 раз.

   {2,} — значение встречается не менее 2 раз.

Их действие распространяется на всё, что находится прямо перед ними. Это может быть обычный символ, например:

Регулярное выражение: lo*
Пример: Are you looking at the lock or the silk?

В примере выше мы ищем символ l, за которым следует символ o ноль или более раз. Вот почему l в слове silk также является совпадением (это l, за которым идёт символ o ноль раз).

Или это может быть метасимвол, например:

Регулярное выражение: l.*k
Пример: Are you looking at the lock or the silk?

На первый взгляд такой результат может показаться вам немного странным. Регулярное выражение .* соответствует повторению ноль или более раз любого символа. Вы могли бы подумать, что при нахождении первого k, будет сказано «да, я нашёл совпадение», но на самом деле говориться, что «k является любым символом, поэтому давайте посмотрим, на сколько длинным может быть соответствие», и поиск продолжится, пока не будет найдет последний k в строке.

Это то, что называется жадным сопоставлением. Это нормальное поведение — пытаться найти самую большую строку, которая может соответствовать шаблону. Мы можем изменить это поведение и сделать его не жадным, поместив вопросительный знак (?) после мультипликатора (что может показаться немного запутанным, поскольку вопросительный знак сам по себе является множителем):

Регулярное выражение: l.*?k
Пример: Are you looking at the lock or the silk?

Экранирование

Иногда нам может потребоваться найти один из символов, который является метасимволом. Для этого мы используем то, что называется экранированием. Поместив обратную косую черту (\) перед метасимволом, мы можем удалить его особое значение. Допустим, что нам нужно найти появление слова this, которое является последним словом в предложении.

Если бы мы сделали следующее:

Регулярное выражение: this.
Пример: Surely this regular expression should match this.

То нашли бы this. как в конце предложения, так и в начале, потому что точка в регулярном выражении обычно соответствует любому символу.

Решением будет следующее:

Регулярное выражение: this\.
Пример: Surely this regular expression should match this.

Совет: Когда метасимволы являются частью вашей искомой строки, то очень легко забыть об их экранировании. Если в результатах ваших регулярных выражений что-то не то, то внимательно обследуйте метасимволы, которые вы, возможно, забыли экранировать.

Механизм работы регулярных выражений


Теперь, когда у вас есть представление о том, что такое регулярные выражения, мы можем рассмотреть то, что происходит под капотом.

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

Заключение

Резюмируем то, что мы узнали:

   . — соответствует любому символу;

   [ ] — совпадает с символом из диапазона, содержащегося в квадратных скобках;

   [^] — соответствует символам, которые не входят в диапазон, содержащийся в квадратных скобках;

   * — совпадение 0 или более раз с указанным элементом;

   + — совпадение 1 или более раз с указанным элементом;

   ? — совпадение 0 или 1 раз с указанным элементом;

   {n} — точное совпадение n раз указанного элемента;

   {n, m} — точное совпадение от n до m раз указанного элемента;

   {n, } — точное совпадение n или более раз указанного элемента;

   \ — экранирование или отмена специального значения указанного символа.

Оценить статью:

Звёзд: 1Звёзд: 2Звёзд: 3Звёзд: 4Звёзд: 5 (6 оценок, среднее: 5,00 из 5)
Загрузка...

Добавить комментарий

Ваш E-mail не будет опубликован. Обязательные поля помечены *

telegram канал
НОВОСТИ RAVESLI