Главная » Регулярные выражения в C++: Использование библиотеки PCRE
Поддержка  регулярных  выражений очень полезна в CGI-программировании.
   В C++ отсутствуют встроенные механизмы для работы с ними. Разработчик,
   однако,  может  воспользоваться  библиотекой  Perl  Compatible Regular
   Expressions (PCRE), ее исходные коды и документация находятся на сайте
   http://www.pcre.org.
Установка   Дистрибутив  содержит подробное описание процесса установки библиотеки
   как   в юникс-системах,   так   и под   Windows.   В последнем  случае
   потребуется  предварительно  немного  изменить  исходные  файлы. После
   компиляции   появятся  библиотеки  pcre.lib  и pcreposix.lib,  которые
   следует подключать к проектам, использующим PCRE.
Минимальная программа   Прежде всего нужно подключить заголовочный файл pcre.h.   #include    Для  простоты  зафиксируем  регулярное  выражение  (шаблон)  и строку,
   которая  будет  с ним  сопоставлена, непосредственно в исходном тексте
   программы в двух символьных массивах.          char pattern[] = "e";
          char str[] = "test";
   Если   необходимо   работать   со строками   на русском  языке,  можно
   попытаться  подключить соответствующую локаль. О том, как это сделать,
   рассказано в статье "Локаль в PCRE".   Наконец,  мы готовы  скомпилировать  шаблон. Для этого следует вызвать
   функцию   pcre_compile().  В первом  аргументе  нужно  указать  ссылку
   на строку,  содержащую регулярное выражение. Во втором параметре можно
   указать  различные  атрибуты (соответствующие опциям /igms... в Perl).
   Следующие  два  параметра  возвращают расшифровку сообщения об ошибках
   компиляции. В последнем аргументе ожидается NULL или ссылку на таблицу
   локали.  В случае  успеха  функция  вернет указатель на структуру типа
   pcre.          pcre *re;
          int options = 0;
          const char *error;
          int erroffset;
          re  =  pcre_compile ((char *) pattern, options, &error, &erroffset, NULL);
   Примечание.  Может  оказаться  так,  что в поставку с компилятором уже
   входит библиотека PCRE. Однако, конкретная реализация может отличаться
   от оригинальной.   В частности,   некоторые   популярные   компиляторы
   в определении функции pcre_exec() обходятся без параметра options.   Если  при  компиляции  шаблона  произошла  ошибка, переменная re будет
   содержать значение NULL.          if (!re){
             cout << "Failedn";
          }
   Если  ошибки  нет,  можно  вызывать  функцию  pcre_exec()  для  поиска
   совпадений. В первом аргументе передают значение, возвращенное функций
   pcre_compile().   Следующие  три  аргумента --  анализируемая  строка,
   ее длинна  и смещение, начиная с которого будет обрабатываться строка.
   Далее   идет   параметр,   указывающий  опции  (их подробное  описание
   приведено  в документации).  В последних двух аргументах нужно указать
   ссылку на массив целых чисел и его длину.          else{
             int count = 0;
             int ovector[30];
             count  =  pcre_exec  (re,  NULL, (char *) str, 4, 0, 0, ovector, 30);
   После  работы  функция  возвратит  число  совпадений или отрицательное
   число в случае ошибки.             if (!count){
                cout << "No matchn";
   Если  найдены  совпадения,  то в  массиве  ovector будут записаны пары
   индексов,   указывающих   на начало  и конец  совпадений.  Первые  два
   элемента  массива  описывают  положение  всего  совпавшего  выражения.
   Остальные  пары --  положение  подстрок, которые совпали с выражениями
   в круглых скобках в шаблоне (это аналоги переменных вида $1 в Perl).   Размер  массива  индексов  произволен,  но он должен быть кратен трем.
   Длина  определяет максимальное число строк, которые можно получить при
   сопоставлении  с шаблоном,  если  в нем встретятся подстроки в круглых
   скобках.   В нашем примере (шаблон e и строка test) найдется совпадение со второй
   буквой  в строке. Поэтому первые два элемента массива ovector содержат
   числа  1 и 2,  то есть  указывают на совпадение, начинающееся в первой
   позиции   строки  и заканчивающееся  во второй.  Индексация  элементов
   в символьных массивах C++ начинается с нуля.   Если  шаблон  содержит  строку (e), в массиве ovector значимыми станут
   две  пары  индексов, причем в этом случае они совпадут, поскольку весь
   шаблон полностью заключен в круглые скобки.   Рассмотрим  еще  один  простой  пример,  записав  регулярное выражение
   e(.)t. Шаблон совпадет с подстрокой est, а в первую переменную попадет
   подстрока s. Поскольку теперь совпадение начинается с первого символа,
   а длина  совпавшей  части  равна трем, в первых двух элементах массива
   ovector  появятся  значения  1 и 4. Следующая  пара --  2 и 3 (то есть
   подстрока единичной длины, начинающаяся во второй позиции образца).
  Полный код   Код  простейшей программы приведен ниже. Шаблон и строка зафиксированы
   в ее теле. Программа выводит только пары индексов из массива ovector.
   #include
   #include
   int main(){
      char pattern[] = "e";
      char str[] = "test";
      const unsigned char *tables = NULL;
      setlocale (LC_CTYPE, (const char *) "ru.");
      tables = pcre_maketables();
      pcre *re;
      int options = 0;
      const char *error;
      int erroffset;
      re  =  pcre_compile ((char *) pattern, options, &error, &erroffset, NULL);
      if (!re){
         cout << "Failedn";
      }
      else{
         int count = 0;
         int ovector[30];
         count  =  pcre_exec  (re,  NULL, (char *) str, 4, 0, 0, ovector, 30);
         if (!count){
            cout << "No matchn";
         }
         else{
            for (int c = 0; c < 2 * count; c += 2){
               if (ovector[c] < 0){
                  cout << "n";
               }
               else{
                  cout << ovector[c] << "/" << ovector[c + 1] << "n";
               }
            }
         }
      }
      return 0;
   } 
    Каждый день специально обученный скрипт обращается к Яндексу и ищет
   этот материал на других серверах.
    © webcode.ru <mail@webcode.ru.> 
Локаль в PCREКак построить локаль для правильной работы функций PCRE.   В предыдущей статье было рассказано о том, как применять библиотеку
   PCRE    (Perl    Compatible    Regular    Expressions)    в программах
   на C++. Здесь же   рассказано,   как  организовать  работу  библиотеки
   с текстами   на русском   языке.   Одна   из первоочередных   задач --
   обеспечить   правильную   работу   функций  с игнорированием  регистра
   символов.  Установка локали   Если  обратиться  к  определению  функции  pcre_compile(),  то следует
   обратить внимание на последний аргумент tableptr:       pcre* pcre_compile (const char *pattern,
          int options,
          const char **errptr,
          int *erroffset,
          const unsigned char *tableptr);
   Если  при  вызове  этой  функции установить последний аргумент в NULL,
   библиотека  воспользуется  собственной  таблицей  pcre_default_tables,
   которая    определена    в файле    chartables.c,    в свою    очередь
   вкомпилированный в библиотечный модуль pcre.lib.   Настроить локаль для работы с национальным алфавитом можно как минимум
   двумя   способами.   Во-первых,  можно  исправить  упомянутую  таблицу
   до компиляции   библиотеки.   Второй  способ  более  универсален,  его
   и рассмотрим.   Сформировать    правильную    таблицу    локали    помогает    функция
   pcre_maketables().     Она     не требует     передачи     аргументов,
   но <<подсознательно>>   учитывает   текущую   локаль.  Поэтому,  чтобы
   построить  необходимую  таблицу,  вначале  следует  установить  локаль
   обычными  средствами,  доступными  в программе на C++, а затем вызвать
   pcre_maketables()   и сохранить  возвращенный  результат --  указатель
   на таблицу   локали.   Этот  указатель  следует  передать  в последнем
   аргументе при вызове функции pcre_compile():       setlocale (LC_CTYPE, "Russian_Russia.1251");
       const unsigned char *locale_tables = pcre_maketables();
       re    =    pcre_compile    (pattern,   options,   errptr,   erroffset, locale_tables);
   Обратите  внимание  на то, что  после  того,  как  построена  таблица,
   функции библиотеки PCRE не учитывают текущую локаль, а работают только
   с этой  таблицей.  Это  свойство  можно  с успехом использовать, чтобы
   не нарушать    работу   остальных   функций,   пользующихся   локалью.
   В следующем  примере  строится  таблица  необходимой  локали,  а затем
   устанавливается локаль, действующая ранее:       char *current = setlocale (LC_CTYPE, NULL);
       char *res = setlocale (LC_CTYPE, locale_string);
       if (!res) return false;
       locale_tables = pcre_maketables();
       setlocale (LC_CTYPE, current);
       if (!locale_tables) return false;
   Переменная   locale_string   содержит   имя  локали.  О том,  как  его
   построить, рассказано в статье "Локаль I".   Не следует  забывать также и о том, что по окончании работы с таблицей
   locale_tables ее следует удалить:       delete locale_tables;
    Каждый день специально обученный скрипт обращается к Яндексу и ищет
   этот материал на других серверах. Категория:
Языки программирования | Просмотров: 230