Levenshtein:MySQL + PHP
$word = strtolower($_GET['term']); $lev = 0; $q = mysql_query("SELECT `term` FROM `words`"); while($r = mysql_fetch_assoc($q)) { $r['term'] = strtolower($r['term']); $lev = levenshtein($word, $r['term']); if($lev >= 0 && $lev < 5) { $word = $r['term']; } }
我怎样才能将所有这一切只移动到一个查询? 不希望通过所有术语进行查询,并在PHP中进行过滤。
你需要在MySQL中使用levenshtein函数,并且像这样查询
$word = mysql_real_escape_string($word); mysql_qery("SELECT `term` FROM `words` WHERE levenshtein('$word', `term`) BETWEEN 0 AND 4");
在MySQL中有两种实现Levenshtein函数的方法。 首先是创build一个存储function,其操作非常像一个存储的事务,除了它有不同的input和输出。 这对于小数据集来说很好,但对接近数千行的任何东西都有点缓慢。 你可以在这里find更多的信息: http : //kristiannissen.wordpress.com/2010/07/08/mysql-levenshtein/
第二种方法是在C / C ++中实现用户自定义函数,并将其作为共享库(* .so文件)链接到MySQL中。 此方法也使用STORED FUNCTION来调用库,这意味着对于这个或第一个方法的实际查询可能是相同的(提供两个函数的input是相同的)。 你可以在这里find关于这个方法的更多信息: http : //samjlevy.com/mysql-levenshtein-and-damerau-levenshtein-udfs/
使用这些方法之一,您的查询将是类似于:
SELECT term FROM words WHERE levenshtein(term, 'term') < 5;
此外,请记住,“阈值”值应相对于原始单词长度而改变。 最好从百分比的angular度来考虑,比如半个字= 50%,半个字= 2。
如果你有一个庞大的数据库,你可以先使用SOUNDEX过滤这些单词:
$word = strtolower(mysql_real_escape_string($_GET['term'])); $rs = mysql_query("SELECT LOWER(`term`) FROM `words` WHERE SOUNDEX(term) = SOUNDEX(" . $word . ")"); while ($row = mysql_fetch_assoc($rs)) { $lev = levenshtein($word, $row['term']); .... }
如果你有足够的时间来玩C扩展或程序,你可能会获得更好的性能,但是在应用真正的levenshtein之前过滤mysql上的logging会使事情变得更快,而且几乎不费吹灰之力。
如果你正在处理非常大的数据集,我发现在PHP中处理Levenshtein操作和sorting比在MySQL中更有效率。 例如查询约1000条logging:
MySQL(〜0.0050s) – > PHP Levenshtein(〜1.300s)
与
MySQL Levenshtein(> = 5.000s) – > PHP(〜0.250s)
还有许多其他的select来优化search引擎,但是如果你想使用Levenshtein只是要知道你将要处理的数据和你想要的延迟。
你可以使这个代码看起来更整洁,但@profitphp是正确的,你不能在没有levenstein库的情况下在MySQL中执行它。
$ word = strtolower($ _ GET ['term']); $ q = mysql_uqery(“SELECT LOWER(`term`)FROM`words`”); while($ r = mysql_fetch_assoc($ q)){ $ lev = levenshtein($ word,$ r ['term']); .... }
我build议你在查询中joinlevenshtein(link: http : //www.artfulsoftware.com/infotree/queries.php#552 )。
您应该使用mysqli_query($ q),因为mysql_query($ q)已被弃用,并可能在未来的PHP版本中被删除!
$word = mysql_real_escape_string($word); $query = "SELECT `term` FROM `words` WHERE levenshtein('$word', `term`) BETWEEN 0 AND 4"; mysqli_qery($query);
我在Oracle中通过在可以调用的函数内部实现PL / SQL中的algorithm来实现这一点。
这是一个查询。 如果你问是否可以将levenshteinfunction移动到mysql,你不能。
好的,你可以,但是它不是比在PHP中做的更简单。
http://www.artfulsoftware.com/infotree/queries.php?&bw=1280#552