我正在努力寻找Gadaffi这个词.搜索此内容的最佳正则表达式是什么?
到目前为止,我最好的尝试是:
\b[KG]h?add?af?fi$\b
Run Code Online (Sandbox Code Playgroud)
但我似乎仍然缺少一些期刊.有什么建议?
更新:我在这里找到了一个相当广泛的列表:http://blogs.abcnews.com/theworldnewser/2009/09/how-many-different-ways-can-you-spell-gaddafi.html
以下答案匹配所有30种变体:
Gadaffi Gadafi Gadafy Gaddafi Gaddafy Gaddhafi Gadhafi Gathafi Ghadaffi Ghadafi Ghaddafi Ghaddafy Gheddafi Kadaffi Kadafi Kaddafi Kadhafi Kazzafi Khadaffy Khadafy Khaddafi Qadafi Qaddafi Qadhafi Qadhdhafi Qadthafi Qathafi Quathafi Qudhafi Kad'afi
Chr*_*ejo 274
简单...... (Qadaffi|Khadafy|Qadafi|...... )它是自我记录的,可维护的,并且假设您的正则表达式引擎实际上编译正则表达式(而不是解释它们),它将编译为更混淆的解决方案所具有的相同DFA.
编写紧凑的正则表达式就像使用短变量名来加速程序一样.它只会在你的编译器脑死亡时有所帮助.
Cze*_*ogy 137
\b[KGQ]h?add?h?af?fi\b
阿拉伯语的转录是(Wiki说)"Qaḏḏāfī",所以也许加上一个Q.而一个H("Gadhafi",正如文章(见下文)提到的那样).
顺便问一下,为什么$在正则表达式的最后?
顺便说一句,关于这个主题的好文章:
卡扎菲,卡扎菲还是卡扎菲?为什么利比亚领导人的名字拼写了这么多不同的方式?.
编辑
要匹配您稍后提到的文章中的所有名称,这应该与所有这些名称相匹配.让我们只希望它不会与很多其他东西相匹配:D
\b(Kh?|Gh?|Qu?)[aeu](d['dt]?|t|zz|dhd)h?aff?[iy]\b
Run Code Online (Sandbox Code Playgroud)
tom*_*ham 45
从你的潜在拼写列表中可以注意到的一个有趣的事情是,所包含列表中只有3个Soundex值(如果忽略异常值'Kazzafi')
G310,K310,Q310
现在,那里有误报('Godby'也是G310),但是通过结合有限的metaphone命中,你可以消除它们.
<?
$soundexMatch = array('G310','K310','Q310');
$metaphoneMatch = array('KTF','KTHF','FTF','KHTF','K0F');
$text = "This is a big glob of text about Mr. Gaddafi. Even using compound-Khadafy terms in here, then we might find Mr Qudhafi to be matched fairly well. For example even with apostrophes sprinkled randomly like in Kad'afi, you won't find false positives matched like godfrey, or godby, or even kabbadi";
$wordArray = preg_split('/[\s,.;-]+/',$text);
foreach ($wordArray as $item){
$rate = in_array(soundex($item),$soundexMatch) + in_array(metaphone($item),$metaphoneMatch);
if ($rate > 1){
$matches[] = $item;
}
}
$pattern = implode("|",$matches);
$text = preg_replace("/($pattern)/","<b>$1</b>",$text);
echo $text;
?>
Run Code Online (Sandbox Code Playgroud)
一些调整,并说一些西里尔音译,你会有一个相当强大的解决方案.
Pra*_*h K 27
使用CPAN模块Regexp :: Assemble:
#!/usr/bin/env perl
use Regexp::Assemble;
my $ra = Regexp::Assemble->new;
$ra->add($_) for qw(Gadaffi Gadafi Gadafy Gaddafi Gaddafy
Gaddhafi Gadhafi Gathafi Ghadaffi Ghadafi
Ghaddafi Ghaddafy Gheddafi Kadaffi Kadafi
Kaddafi Kadhafi Kazzafi Khadaffy Khadafy
Khaddafi Qadafi Qaddafi Qadhafi Qadhdhafi
Qadthafi Qathafi Quathafi Qudhafi Kad'afi);
say $ra->re;
Run Code Online (Sandbox Code Playgroud)
这会产生以下正则表达式:
(?-xism:(?:G(?:a(?:d(?:d(?:af[iy]|hafi)|af(?:f?i|y)|hafi)|thafi)|h(?:ad(?:daf[iy]|af?fi)|eddafi))|K(?:a(?:d(?:['dh]a|af?)|zza)fi|had(?:af?fy|dafi))|Q(?:a(?:d(?:(?:(?:hd)?|t)h|d)?|th)|u(?:at|d)h)afi))
Run Code Online (Sandbox Code Playgroud)
Sta*_*erg 23
我觉得你在这里过得很复杂.正确的正则表达式很简单:
\u0627\u0644\u0642\u0630\u0627\u0641\u064a
Run Code Online (Sandbox Code Playgroud)
它匹配形成单词القذافي(即Gadaffi)的七个阿拉伯语Unicode代码点的串联.
and*_*oke 19
如果你想避免匹配没有人使用的东西(即避免倾向于".+"),你最好的方法是创建一个正则表达式,这只是所有的选择(例如.(Qadafi | Kadafi | ...)然后将其编译为DFA,然后将DFA转换回正则表达式.假设一个适度合理的实现将给你一个"压缩"的正则表达式,保证不包含意想不到的变体.
小智 10
如果您已经拥有了所有30种可能性的具体列表,那么只需将它们与一堆"ors"连接在一起即可.然后你可以确定它只匹配你列出的确切内容,而不是更多.您的RE引擎可能会进一步优化,并且有30个选择,即使它不是它仍然不是一个大问题.试图通过手动将其变成"聪明"的RE来摆弄可能不会变得更好并且可能变得更糟.
小智 9
(G|Gh|K|Kh|Q|Qh|Q|Qu)(a|au|e|u)(dh|zz|th|d|dd)(dh|th|a|ha|)(\x27|)(a|)(ff|f)(i|y)
Run Code Online (Sandbox Code Playgroud)
当然不是最优化的版本,拆分音节以最大化匹配,同时努力确保我们不会得到误报.
小智 7
好吧,因为你匹配小词为什么不尝试与Levenshtein距离相似的搜索引擎?您最多可以允许k次插入或删除.通过这种方式,您可以将距离函数更改为对您的特定问题更有效的其他事物.simMetrics库中有许多可用的功能.