我正在开发一个文档系统,每次创建一个新系统时,它必须检测并丢弃大约500.000条记录的数据库中的重复项。
目前,我正在使用搜索引擎检索20个最相似的文档,并将它们与我们尝试创建的新文档进行比较。问题是我必须检查新文档是否相似(使用similar_text很容易),或者即使它包含在其他文本中,所有这些操作都考虑到文本可能已被用户部分更改(这里是问题)。我怎么能这样做?
例如:
<?php
$new = "the wild lion";
$candidates = array(
'the dangerous lion lives in Africa',//$new is contained into this one, but has changed 'wild' to 'dangerous', it has to be detected as duplicate
'rhinoceros are native to Africa and three to southern Asia.'
);
foreach ( $candidates as $candidate ) {
if( $candidate is similar or $new is contained in it) {
//Duplicated!!
}
}
当然,在我的系统中,文件超过3个字:)
答案 0 :(得分:1)
这是我正在使用的时间解决方案:
function contained($text1, $text2, $factor = 0.9) {
//Split into words
$pattern= '/((^\p{P}+)|(\p{P}*\s+\p{P}*)|(\p{P}+$))/u';
$words1 = preg_split($pattern, mb_strtolower($text1), -1, PREG_SPLIT_NO_EMPTY);
$words2 = preg_split($pattern, mb_strtolower($text2), -1, PREG_SPLIT_NO_EMPTY);
//Set long and short text
if (count($words1) > count($words2)) {
$long = $words1;
$short = $words2;
} else {
$long = $words2;
$short = $words1;
}
//Count the number of words of the short text that also are in the long
$count = 0;
foreach ($short as $word) {
if (in_array($word, $long)) {
$count++;
}
}
return ($count / count($short)) > $factor;
}
答案 1 :(得分:0)
您可能进行或进一步调查的一些想法是:
索引文档,然后搜索类似的文档。因此,Solr,Sphinx或Zend Search Lucene等开源索引/搜索系统可以派上用场。
您可以使用sim hashing algorithm或shingling。简而言之,simhash算法将允许您为类似文档计算类似的哈希值。因此,您可以将此值存储在每个文档中,并检查各种文档的相似程度。
您可能会发现有助于从中获取一些想法的其他算法:
2。 Bayesian filtering - SO Questions re Bayesian filtering。此列表项中的第一个链接指向Wiki上的贝叶斯垃圾邮件过滤文章,但此算法可以适应您要执行的操作。