php preg_grep和umlaut/accent
我有一个由术语组成的数组,其中一些包含重音字符。我做了这样的预格雷普php preg_grep和umlaut/accent,php,regex,character-encoding,transliteration,Php,Regex,Character Encoding,Transliteration,我有一个由术语组成的数组,其中一些包含重音字符。我做了这样的预格雷普 $data= array('Napoléon','Café'); $result = preg_grep('~' . $input . '~i', $data); 因此,如果用户输入'le',我还希望结果'Napoléon'匹配,这不适用于ablove命令 我做了一些搜索,发现这个函数可能是相关的 preg_match("/[\w\pL]/u",$var); 我如何将这些结合起来并使其工作?您可以这样写: $data =
$data= array('Napoléon','Café');
$result = preg_grep('~' . $input . '~i', $data);
因此,如果用户输入'le',我还希望结果'Napoléon'匹配,这不适用于ablove命令
我做了一些搜索,发现这个函数可能是相关的
preg_match("/[\w\pL]/u",$var);
我如何将这些结合起来并使其工作?您可以这样写:
$data = array('Napoléon','Café');
// do something with your input, but for testing purposes it will be simply as you wrote in your example
$input = 'le';
foreach($data as $var) {
if (preg_match("/".str_replace(array("é"....), array("e"....), $input)."/i", str_replace(array("é"....), array("e"....), $var)))
//do something as there is a match
}
实际上,在这种情况下甚至不需要正则表达式,简单的strpos就足够了。仅使用正则表达式模式是不可能的。这并不是因为您不能告诉正则表达式引擎匹配所有的“e”和类似项。但是,可以先规范化输入数据(包括数组和搜索输入),然后搜索规范化数据,但返回非规范化数据的结果 在下面的示例中,我使用音译来进行这种规格化,我想这就是您要寻找的:
$data = ['Napoléon', 'Café'];
$result = array_translit_search('le', $data);
print_r($result);
$result = array_translit_search('leó', $data);
print_r($result);
示例性输出是:
Array
(
[0] => Napoléon
)
Array
(
[0] => Napoléon
)
搜索函数本身相当直接,如上所述,音译输入,执行preg\u grep
,然后返回原始输入匹配:
/**
* @param string $search
* @param array $data
* @return array
*/
function array_translit_search($search, array $data) {
$transliterator = Transliterator::create('ASCII-Latin', Transliterator::REVERSE);
$normalize = function ($string) use ($transliterator) {
return $transliterator->transliterate($string);
};
$dataTrans = array_map($normalize, $data);
$searchTrans = $normalize($search);
$pattern = sprintf('/%s/i', preg_quote($searchTrans));
$result = preg_grep($pattern, $dataTrans);
return array_intersect_key($data, $result);
}
此代码需要,您可以用任何其他类似的音译或翻译函数替换它
顺便说一句,我不建议在这里使用
str\u replace
,如果您需要返回到翻译表,请使用。这就是你要找的。但是我更喜欢一个自带翻译的库,特别是如果是Intl库,你通常无法打败它。什么是var\u dump($input)代码>给予?您没有在问题中提供这一点。$input实际上是用户输入的内容,在上面的例子中是“le”。但这是两个不同的字符串。le
应该如何匹配lé
,这是不同的。这应该遵循哪条规则?你猜这两件事可能会起作用,我认为你根本无法将它们结合起来。是什么让你认为这样的组合是可能的?请同时提供\pL
和preg.*
函数的参考,您在这里指的是什么?您可以在twitter引导typeahead(自动完成)中找到类似的函数。其基本思想是,即使用户类型“cafe”、“Café”也应作为建议返回。您可以首先在用户输入和数据(在时间变量中)中替换所有字符,如é(它们不可能很多),然后您的正则表达式将完全工作。非常感谢。这确实是一个可行的解决办法。我仍然在看是否有办法在一个正则表达式行中完成它。@user1906418如果你要使用此解决方案,最好在$input
中组合替换字符,并继续使用preg_grep()
不要使用str_replace
来完成此工作,如果你真的需要,请使用。非常感谢你的详细回答!对于strtr vs str_replace问题,它们执行的不是相同的操作吗?是因为性能还是其他原因,strtr更好?是因为这些函数做了一些不同的事情。您需要的是翻译,而不是替换,在替换的字符串中替换,然后在已经替换了两次的字符串中再次替换。你只需要翻译,而不是那些倍数。就性能而言,我不知道。也许strtr也更快,但谁在乎呢?