note 109564 added to function.similar-text

From: Date: Sun, 29 Jul 2012 05:50:14 +0000
Subject: note 109564 added to function.similar-text
Groups: php.notes 
Request: Send a blank email to php-notes+get-189449@lists.php.net to get a copy of this message
To spam hater and others: this function has been broken for a very long time. The devs unfortunately keep ignoring it. Not only swapping the two strings give different results, it gives wrong results too. http://bugs.php.net/bug.php?id=62648 <?php echo similar_text("test", "cert"); echo ","; echo similar_text("cert", "test"); ?> Prints 1,2 instead of 2,2. Also: <?php $s1 = 'biocompatibilitystudiesofironoxidedextrinthinfilmsbacdetundgakslfnnd'; $s2 = 'studyofironoxidenanoparticlescoatedwithdextrinobtainedbybcgagsfddteuhdgavdjfkdbey'; echo similar_text($s1, $s2); echo ","; echo similar_text($s2, $s1); ?> Prints 34,32 instead of 35,35. Both are wrong! The similar_text() function computes the length of the longest subsequence; google "longest subsequence problem" (LCS). In the above case, that is "studofironoxidedextrintinbcdtudgafd" which has 35 chars. The earlier implementation in these comments of an LCS length function didn't actually work for me. Here's a functional and direct replacement of the broken similar_text(). Note it is much slower than similar_text(), since similar_text is a native C function, but that's buggy and this works: <?php function similar_text_fix ($str1, $str2, &$percent = null) { $len1 = strlen($str1); $len2 = strlen($str2); // two-dim array, init first row and column to zero $a = array_fill(1, $len1, array(0)); $a[0] = array_fill(0, $len2 + 1, 0); for ($i = 1; $i <= $len1; ++$i) for ($j = 1; $j <= $len2; ++$j) if ($str1{$i-1} == $str2{$j-1}) $a[$i][$j] = $a[$i-1][$j-1] + 1; else $a[$i][$j] = $a[$i][$j-1] > $a[$i-1][$j] ? $a[$i][$j-1] : $a[$i-1][$j]; $percent = $a[$len1][$len2] * 200 / ($len1 + $len2); return $a[$len1][$len2]; } ?> Here's a test: <?php echo similar_text($s1, $s2, $p); echo ","; echo similar_text($s2, $s1); echo ",$p"; // 35,35,46.979865771812 ?> Regards Regards ---- Server IP: 69.147.83.197 Probable Submitter: 131.111.7.72 ---- Manual Page -- http://www.php.net/manual/en/function.similar-text.php Edit -- https://master.php.net/note/edit/109564 Del: integrated -- https://master.php.net/note/delete/109564/integrated Del: useless -- https://master.php.net/note/delete/109564/useless Del: bad code -- https://master.php.net/note/delete/109564/bad+code Del: spam -- https://master.php.net/note/delete/109564/spam Del: non-english -- https://master.php.net/note/delete/109564/non-english Del: in docs -- https://master.php.net/note/delete/109564/in+docs Del: other reasons-- https://master.php.net/note/delete/109564 Reject -- https://master.php.net/note/reject/109564 Search -- https://master.php.net/manage/user-notes.php

« previous php.notes (#189449) next »