Рано или поздно каждый веб разработчик сталкивается с задачей внедрения в свой код регулярных выражений. Многие думают, что составлять их невероятно сложно и под силу только избранным. На самом деле это не так. И сегодня я покажу Вам как составлять регулярные выражения.
Но для начала немного общей информации. Что такое регулярные выражения и для чего они нужны?
Регулярные выражения (англ. regular expressions) — формальный язык поиска и осуществления манипуляций с подстроками в тексте, основанный на использовании метасимволов (символов-джокеров, англ. wildcard characters). По сути это строка-образец (англ. pattern, по-русски её часто называют «шаблоном», «маской»), состоящая из символов и метасимволов и задающая правило поиска.
Выписка из Википедии
Другими словами, регулярное выражение означает регулярную последовательность символов или чисел или какого-нибудь другого шаблона, то есть выражение, которое нужно найти.
Регулярные выражения наиболее часто используются для поиска и подстановки текста, с их помощью можно проверять правильность введенной пользователем информации, дабы избежать ввода некорректной информации или информации в неподходящем формате.
Принцип их работы достаточно прост.
Во-первых, задается строка, в которой будет производиться поиск. Во-вторых, создается шаблон этого самого поиска.
И если Вы знаете как правильно создать шаблон под ту или иную задачу, то при помощи регулярных выражений Вы может найти практически все, что угодно.
Давайте научимся создавать регулярные выражения для php
Будем разбирать сразу все на практике и смотреть на полученные результаты.
Я создаю новый php файл для тестирования всего кода. Вы можете сделать то же самое. Создайте файл и пропишите в нем между тегов body открывающий и закрывающий теги для php кода:
<?php между этими тегами будет весь наш код ?>
Сразу запустите файл в браузере (убедитесь, что Ваш Денвер работает). Если Вы не знаете, то для запуска файла, нужно прописать в командной строке браузера localhost/имя папки, в которой лежит файл/имя файла.php.
Итак, начнем с самого начала. Для начала я напишу текст, в котором буду икать соответствия и помещу его в переменную (конечно же текст должен быть заключен в кавычки).
$string_search = "За последние несколько дней в сети интернет появились новые сайты, такие как www.mysite.ru, http://website.com и еще очень интересный сайт www.yoursite.ru. В 2014 году мы планируем запустить в интернет сайт под названием http://www.sitesite.com, а уже к началу 2015 года мы подведем статистику о его посещаемости. По вопросам обращайтесь на email admin@yandex.ru или myadmin@hotmail.com.";
Вот такой вот текст. Теперь нужно создать шаблон нашего регулярного выражения.
Давайте пойдем от простого к сложному. Для начала поищем в тексте слово «интернет», узнаем сколько раз оно встречается и выведем на экран.
Для этого давайте составим простой шаблон регулярного выражения и поместим его в переменную.
Начнем с того, что регулярное выражение – это простая строка, и ее нужно взять в кавычки.
Кроме того, регулярные выражения начинаются и заканчиваются с прямого слэша. То, что находится между слешами и составляет суть регулярного выражения.
Таким образом, давайте вставим в наш код самый простейший шаблон регулярного выражения, занесенный в переменную:
$regex = "/интернет/";
Но это всего лишь переменные. А теперь самое главное!
Пропишем функцию, которая будет искать соответствия в нашем тексте по нашему регулярному выражению.
В PHP для этого используется специальная функция «preg_match».
Функция preg_match и функция preg_match_all.
В функцию preg_match передаются 2 параметра: регулярное выражение и строка, в которой нужно вести поиск.
Эта функция может вернуть значения: либо 0 (если совпадения отсутствуют), либо 1 (при обнаружении первого совпадения, а потом просто останавливает поиск).
Если же нам требуются все соответствия с шаблоном, то нужно использовать функцию preg_match_all.
В функцию preg_match_all передаем 3 параметра: регулярное выражение; строка, в которой ведем поиск; переменная, в которую поместим результаты поиска.
Так как нам нужны все совпадения, имеющиеся в тексте, то мы будем использовать функцию preg_match_all. Следовательно, наш код пополнится следующей строкой:
$result = preg_match_all($regex, $string_search, $out);
Осталось вывести на экран результат. Я предлагаю сначала вывести число совпадений, а потом и сами эти совпадения в цикле for (возможно на практике вывод результатов Вам и не понадобиться, но в этом уроке я делаю его для наглядности).
Добавим к нашему коду следующие строки:
echo $result ."<br/>"; for($i=0; $i<$result; $i++) { echo $out[0][$i]."<br/>"; }
Теперь если проверить страницу в браузере, то мы увидим следующий результат:
Если нам нужно найти одно значение или другое, например, мы хотим найти слово «интернет» или «сайт», то между искомыми значениями в шаблоне нужно поставить специальный символ «|». В таком случае, регулярное выражение будет выглядеть так:
$regex = "/интернет|сайт/";
А результат на экране мы увидем такой:
Но это все очень просто. Давайте займемся чем-то посложнее, например найдем все адреса сайтов, прописанных в нашем тексте. Обратите внимание, что они прописаны в разных форматах (одни с www, другие с http:// и даже с http://www.. Одни заканчиваются на .ru, другие на .com). Согласитесь, это уже интереснее! Давайте начнем.
Предлагаю начать с конца.
1. Для начала давайте скажем нашему шаблону вывести все с .ru или с .com.
Сделаю небольшое отступление и скажу, что точка (.) в регулярных выражениях обозначает – «любой символ», поэтому точку нужно экранировать. Сделать мы это можем при помощи обратного слэша (\). С символом или (|) Вы уже знакомы.
Пока получается вот так:
$regex = "/(\.ru)|(\.com)/";
И действительно, шаблон найдет нам все, что заканчивается на эти символы. Помимо адресов веб сайтов он также учтет и адреса электронной почты, так как они тоже заканчиваются на эти символы. Но далее мы это исправим.
2. Теперь укажем, что перед .ru или .com могут стоять символы латинского алфавита от a до z, также цифры от 0 до 9 и знак «-». Это будет выглядеть так: [a-z0-9-]. А еще нам нужно указать квантор (простыми словами: то, сколько таких символов может быть). Например, если я напишу так: {2,} – это будет значить 2 или больше.
Осталось все это объединить. Кстати перед этим нужно заключить уже имеющуюся часть (\.ru)|(\.com) в скобки. Если мы этого не сделаем, то все, что мы намишем впереди будет относиться только к .ru.
Объединяя все вышесказанное, получим такой код:
$regex = "/[a-z0-9-]{2,}((\.ru)|(\.com))/";
А на экране увидем следующее:
Уже лучше, но шаблон по-прежнему выдает нам также и адреса электронной почты. Сейчас мы это исправим.
3. Теперь нам нужно выбирать только те совпадения, которые будут начинаться либо с www., либо с http://. Так мы исключим из нашего списка выдачу адресов электронной почты, которые туда попали.
Что для этого нужно сделать?
Следующая часть выражения будет стоять в самом начале (помните, мы идем от конца к началу), ее мы заключим в скобки. Далее в скобках пропишем, что нас интересует http:// (слэши здесь тоже нужно экранировать) или (|) www. (точку тоже нужно экранировать). После скобок откроем фигурные скобки и пропишем квантор ({1} – значит это выражение должно встречаться ровно один раз). Получается вот такой код:
$regex = "/((http:\/\/)|(www\.)){1}[a-z0-9-]{2,}((\.ru)|(\.com))/";
Теперь, если обновить страничку в браузере, то мы увидем, что в результате нам показываются только адреса веб сайтов, как и было задумано:
Теперь, я думаю, что Вам стало понятно, как составить такое регулярное выражение. Оно, конечно же не универсально, я просто придумала его для примера. Уверена, что если посидеть и хорошенько подумать, то можно его усовершенствовать.
Вообще, составление регулярного выражения похоже на составление уровнения.
Давайте рассмотрим еще один простой пример.
Найдем все упоминания годов в нашем тексте.
Сделать это необычайно просто.
Год должен состоять из цифр. Для этого мы будем использовать символьный класс (\d). Этот символьный класс обозначает – «Цифра». Кроме того, год должен состоять из четырех цифр, а для этого мы будем использовать квантор {4}.
В итоге, регулярное выражение будет выглядеть вот так:
$regex = "/(\d{4})/";
А в результате мы получим вывод всех годов, встречающихся в тексте (у нас их в тексте два):
На последок я хочу Вам предложить один очень неплохой ресурс, который поможет Вам в изучении регулярных выражений. Называется он regexlib.com .
В нем есть тестер регулярных выражений. То есть вы можете писать регулярные выражения и тестировать их работу прямо в этом ресурсе. Для этого нужно перейти на вкладку «Redex Tester», в поле «Source» нужно прописать тот текст, в котором будет производиться поиск. А в поле «Regular Expression» нужно писать само регулярное выражение. Обратите внимание, что когда будете писать регулярное выражение, то вводить “//” в поле не нужно. Сразу пишите само регулярное выражение. После написания нажимаете на кнопку «Submit» и смотрите результаты. Это очень удобно!
Кроме того, на сервисе Вы можете найти примеры регулярных выражений. Для этого нужно перейти на вкладку «Browse Expressions» и Вы увидите синенькие кнопочки, обозначающие категории регулярных выражений для разных задач. Вы можете воспользоваться готовыми решениями для Ваших веб проектов, а также (если Вам действительно хочется научиться их составлять самому) поразбираться в них.
На самом деле о регулярных выражениях можно писать очень много, но хочется сказать, что чтобы научиться писать их быстро и эффективно нужно практиковаться. Практикуйтесь! Ведь так приятно, когда запускаешь скрипт, а он работает как надо!
Подписывайтесь на обновление блога, обещаю Вам много всего интересного! А также жду Ваших комментариев, вопросов и предложений.
Удачи! И до новых встреч!