Использование preg_replace / preg_match с символами UTF-8 - в частности, макронами маори - PullRequest
0 голосов
/ 05 августа 2010

Я пишу некоторую функцию автозаполнения, которая предлагает имена страниц, которые относятся к терминам, введенным в поле поиска на нашем веб-сайте.

Например, при вводе слова "мусор" можно было бы предложить "Мусор и переработка", "Центры сбора мусора" и т. Д.

Я сталкиваюсь с проблемой, что некоторые из имен наших страниц включают макроны - в частности, макрон, используемый для правильного написания "маори" (коренные жители Новой Зеландии).

Пользователи будут вводить слово «маори» в поле поиска, и я хочу иметь возможность возвращать такие страницы, как «История маори».

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

preg_match('/\m(.{1})ori/i',$page_title)

Который также возвращает заголовки страниц, содержащие «Причалы», но не «Маори». Как preg_match / preg_replace видит такие символы, как «ā», и как мне построить регулярное выражение, чтобы подобрать их?

Приветствие Tama

Ответы [ 2 ]

1 голос
/ 05 августа 2010
  1. Используйте модификатор /u для режима utf-8 в регулярных выражениях,
  2. В целом вам лучше всего сделать iconv('utf-8','ascii//TRANSLIT',$string) как для имени и поиска, так и для сравнения.
0 голосов
/ 05 августа 2010

Одна вещь, которую вы должны помнить, это то, что UTF-8 дает вам многобайтовые символы для всего, что находится за пределами ASCII. Я не знаю, обрабатывается ли строка $page_title как объект Unicode или как немая строка байтов. Если это опция строки байтов, вам придется сделать двойные точки, чтобы поймать ее, или {1,4}. И даже тогда вам придется проверять до четырех байтов, которые вы перебираете между M и o, для формирования единственного действительного символа UTF-8. Это все спорно, если PHP делает Юникод право, я не использовал его в годах, так что я не могу поручиться за него.

Другая проблема, которую следует рассмотреть, заключается в том, что А можно построить двумя способами; один как один символ (U + 0101) и один как ДВА символа юникода («а» плюс диакритический знак в диапазоне U + 0300). Вы, вероятно, только собираетесь когда-либо получить первое, но знайте, что второе также возможно.

Единственный язык, который мне известен, который надежно справляется с этим, - это Perl 6, в котором есть все виды безумных модификаторов для интернационализированного текста в регулярных выражениях.

...