Регулярные алгоритмы экспрессии<regex_match
>,<regex_search
>и<regex_replace
>все ожидают, что последовательность символов, на которой они действуют, кодируется в том же самом кодировании символа, что и объект регулярного выражения, с которым они используются. Для регулярных выражений Unicode поведение нежелательно: хотя мы можем захотеть обрабатывать данные в «кусках» UTF-32, фактические данные гораздо чаще кодируются как UTF-8 или UTF-16. Таким образом, заголовокобеспечивает ряд тонких оберток вокруг этих алгоритмов, называемых<u32regex_match
>,<u32regex_search
>и<u32regex_replace
>. Эти обертки используют внутренние итераторы, чтобы внешние данные UTF-8 или UTF-16 выглядели так, как будто это действительно последовательность UTF-32, которая затем может быть передана «реальному» алгоритму.
Для каждого<regex_match
>алгоритма, определенного<<boost/regex.hpp>
>, затем<<boost/regex/icu.hpp>
>определяет перегруженный алгоритм, который принимает те же аргументы, но который называется<u32regex_match
>, и который принимает закодированные данные UTF-8, UTF-16 или UTF-32, а также UnicodeString ICU в качестве ввода.
Пример: сопоставить пароль, закодированный в UTF-16 UnicodeString:
bool is_valid_password(const UnicodeString& password, const UnicodeString& requirements)
{
return boost::u32regex_match(password, boost::make_u32regex(requirements));
}
Пример: сопоставьте кодированное имя файла UTF-8:
std::string get_filename(const std::string& path)
{
boost::u32regex r = boost::make_u32regex("(?:\\A|.*\\\\)([^\\\\]+)");
boost::smatch what;
if(boost::u32regex_match(path, what, r))
{
return what.str(1);
}
else
{
throw std::runtime_error("Invalid pathname");
}
}
Для каждого<regex_search
>алгоритма, определенного<<boost/regex.hpp>
>, затем<<boost/regex/icu.hpp>
>определяет перегруженный алгоритм, который принимает те же аргументы, но который называется<u32regex_search
>, и который принимает закодированные данные UTF-8, UTF-16 или UTF-32, а также UnicodeString ICU в качестве ввода.
Пример: поиск последовательности символов в определенном языковом блоке:
UnicodeString extract_greek(const UnicodeString& text)
{
boost::u32regex r = boost::make_u32regex(
L"[\\x{370}-\\x{3FF}](?:[^[:L*:]]|[\\x{370}-\\x{3FF}])*");
boost::u16match what;
if(boost::u32regex_search(text, what, r))
{
return UnicodeString(what[0].first, what.length(0));
}
else
{
throw std::runtime_error("No Greek found!");
}
}
Для каждого<regex_replace
>алгоритма, определенного<<boost/regex.hpp>
>, затем<<boost/regex/icu.hpp>
>определяет перегруженный алгоритм, который принимает те же аргументы, но который называется<u32regex_replace
>, и который принимает закодированные данные UTF-8, UTF-16 или UTF-32, а также UnicodeString ICU в качестве ввода. Последовательность ввода и спецификатор строки формата, переданный алгоритму, могут быть закодированы независимо (например, один может быть UTF-8, другой в UTF-16), но в аргументе итератора строки/выхода результата должно использоваться то же кодирование символов, что и в искомом тексте.
Пример: номер кредитной карты переформатировать:
const boost::u32regex e = boost::make_u32regex(
"\\A(\\d{3,4})[- ]?(\\d{4})[- ]?(\\d{4})[- ]?(\\d{4})\\z");
const char* human_format = "$1-$2-$3-$4";
UnicodeString human_readable_card_number(const UnicodeString& s)
{
return boost::u32regex_replace(s, e, human_format);
}