soundex

(PHP 4, PHP 5, PHP 7, PHP 8)

soundex计算字符串的 soundex 键

描述

soundex(string $string): string

计算 string 的 soundex 键。

Soundex 键具有以下属性:发音相似的单词会产生相同的 soundex 键,因此可以用来简化数据库搜索,在这些数据库中,您知道发音但不知道拼写。

此 soundex 函数是 Donald Knuth 在 "The Art Of Computer Programming, vol. 3: Sorting And Searching", Addison-Wesley (1973), pp. 391-392 中描述的函数之一。

参数

string

输入字符串。

返回值

返回一个包含四个字符的 soundex 键作为 string。如果 string 中至少包含一个字母,则返回的字符串以字母开头。否则返回 "0000"

变更日志

版本 描述
8.0.0 在此版本之前,使用空字符串调用该函数会导致返回 false,没有特别的原因。

示例

示例 #1 Soundex 示例

<?php
soundex
("Euler") == soundex("Ellery"); // E460
soundex("Gauss") == soundex("Ghosh"); // G200
soundex("Hilbert") == soundex("Heilbronn"); // H416
soundex("Knuth") == soundex("Kant"); // K530
soundex("Lloyd") == soundex("Ladd"); // L300
soundex("Lukasiewicz") == soundex("Lissajous"); // L222
?>

参见

添加备注

用户贡献的备注 20 条备注

27
nicolas dot zimmer at einfachmarke dot de
16 年前
由于 soundex() 对德语不能产生最佳结果
我们编写了一个函数来实现所谓的科隆音韵学
(科隆音韵学).

请在下面找到代码,希望它对您有所帮助

<?php
/**
* 用于获取字符串的科隆语音值
*
* 如 http://de.wikipedia.org/wiki/Kölner_Phonetik 所述
* 基于汉斯·约阿希姆·波斯特尔:科隆语音。
* 人名识别方法
* 基于形式分析。
* 在:IBM-Nachrichten,第 19 卷,1969 年,第 925-931 页
*
* 本程序发布的目的是希望它有用,
* 但没有任何担保;甚至没有暗示的适销性或特定用途适用性的担保。
* 有关详细信息,请参阅 GNU 通用公共许可证。
*
* @package phonetics
* @version 1.0
* @link http://www.einfachmarke.de
* @license GPL 3.0 <http://www.gnu.org/licenses/>
* @copyright 2008 by einfachmarke.de
* @author Nicolas Zimmer <nicolas dot zimmer at einfachmarke.de>
*/

function cologne_phon($word){

/**
* @param string $word 要分析的字符串
* @return string $value 代表科隆语音值
* @access public
*/

//准备处理
$word=strtolower($word);
$substitution=array(
"ä"=>"a",
"ö"=>"o",
"ü"=>"u",
"ß"=>"ss",
"ph"=>"f"
);

foreach (
$substitution as $letter=>$substitution) {
$word=str_replace($letter,$substitution,$word);
}

$len=strlen($word);

//例外规则
$exceptionsLeading=array(
4=>array("ca","ch","ck","cl","co","cq","cu","cx"),
8=>array("dc","ds","dz","tc","ts","tz")
);

$exceptionsFollowing=array("sc","zc","cx","kx","qx");

//编码表
$codingTable=array(
0=>array("a","e","i","j","o","u","y"),
1=>array("b","p"),
2=>array("d","t"),
3=>array("f","v","w"),
4=>array("c","g","k","q"),
48=>array("x"),
5=>array("l"),
6=>array("m","n"),
7=>array("r"),
8=>array("c","s","z"),
);

for (
$i=0;$i<$len;$i++){
$value[$i]="";

//例外
if ($i==0 AND $word[$i].$word[$i+1]=="cr") $value[$i]=4;

foreach (
$exceptionsLeading as $code=>$letters) {
if (
in_array($word[$i].$word[$i+1],$letters)){

$value[$i]=$code;

} }

if (
$i!=0 AND (in_array($word[$i-1].$word[$i],
$exceptionsFollowing))) {

value[$i]=8;

}

//正常编码
if ($value[$i]==""){
foreach (
$codingTable as $code=>$letters) {
if (
in_array($word[$i],$letters))$value[$i]=$code;
}
}
}

//删除重复值
$len=count($value);

for (
$i=1;$i<$len;$i++){
if (
$value[$i]==$value[$i-1]) $value[$i]="";
}

//删除元音
for ($i=1;$i>$len;$i++){//省略第一个字符代码和 h
if ($value[$i]==0) $value[$i]="";
}


$value=array_filter($value);
$value=implode("",$value);

return
$value;

}

?>
5
fie at myrealbox dot com
21 年前
administrator at zinious dot com

抱歉,但您的代码不符合 Soundex。
以下是您的代码、我的代码和默认代码的结果。

字符串:rest
R620 执行管理员的功能 0.009452
R230 执行 cg 的功能 0.001779
R230 执行默认 Soundex 功能 9.4999999999956E-005

字符串:reset
R620 执行管理员的功能 0.0055900000000001
R230 执行 cg 的功能 0.00091799999999997
R230 执行默认 Soundex 功能 0.00010600000000005

我不知道为什么默认的,偶尔,会因为某种原因是 9.xxx。我觉得很奇怪。
我的代码在下面。这些测试是在 Soundex 修改之前进行的,正如我将在下面描述的那样。
顺便说一下,有关 Soundex 算法的所有原始规范,请转到
http://www.star-shine.net/~functionifelse/GFD/?word=soundex

dalibor dot toth at podravka dot hr

是的,也许很遗憾它给了你相同的代码。
即使是 Metaphone 也存在这个问题。
但人们可能不希望如此精确。如果有人
在搜索引擎上,我们称之为 Shmoogle,寻找
"php array reset" 并搜索 "php array rest"
那么 Shmoogle 可能会返回有关床的信息等等。
(如果他们都很蠢,没有把第一个词
作为更重要的)总之,Shmoogle 可能需要它在
在这种情况下不太精确。但无论如何。
我的解决方法是在字符串末尾添加音节数,使其长度为 5 个字符。
这将按如下方式工作。

代码地址:http://star-shine.net/~functionifelse/cg_soundex.php

或者,如果您想使用默认的 Soundex 函数

$str = soundex($str).cg_sylc($str);

革命性的或多或少。可能更少。
这个函数只适用于一个词。我想看看有人
修改它以使用 split 并通过循环运行它以获得每个单词的 cg_soundex
那将很有趣;)
我还想建议那些制作 PHP 的 Zend Apache 之类的人
添加一个可选的额外变量,用户可以按如下方式指定

soundex("string",SYL);

这将在字符串末尾返回音节数
高度精确的声音测试,哇!您还可以添加 VOW 用于元音
以及 CONS 用于辅音,或任何其他人想要的东西。
但我真的认为音节数将非常有效。
嗯,如果这对任何人有帮助,欢迎您。嗯,祝您在所有
PHP 冒险中好运。哦,还有最终结果

音节
1 rest
2 reset
Metaphone
RST rest
RST reset
soundex
R230 rest
R230 reset

字符串:rest
R2301 执行 cg 的功能 0.00211
R230 执行默认 Soundex 功能 0.00011299999999997

字符串:reset
R2302 执行 cg 的功能 0.001691
R230 执行默认 Soundex 功能 0.00010399999999999

默认函数的速度稍微快一点。
所以也许他们会添加这个选项,这样我们就可以兼顾速度和准确性。

厄运的静默之风呼啸而过!
17
Dirk Hoeschen - Feenders de
10年前
我改进了一些 niclas zimmer 的“科隆音标”功能。数组的键和值被反转,以使用简单的数组而不是多维数组。因此,所有循环和迭代不再需要找到与字符匹配的值。
我把这个函数放进了一个静态类,并将数组声明移到了函数之外。

结果比原来更可靠,速度提高了五倍。

<?php
class CologneHash() {

static
$eLeading = array("ca" => 4, "ch" => 4, "ck" => 4, "cl" => 4, "co" => 4, "cq" => 4, "cu" => 4, "cx" => 4, "dc" => 8, "ds" => 8, "dz" => 8, "tc" => 8, "ts" => 8, "tz" => 8);

static
$eFollow = array("sc", "zc", "cx", "kx", "qx");

static
$codingTable = array("a" => 0, "e" => 0, "i" => 0, "j" => 0, "o" => 0, "u" => 0, "y" => 0,
"b" => 1, "p" => 1, "d" => 2, "t" => 2, "f" => 3, "v" => 3, "w" => 3, "c" => 4, "g" => 4, "k" => 4, "q" => 4,
"x" => 48, "l" => 5, "m" => 6, "n" => 6, "r" => 7, "c" => 8, "s" => 8, "z" => 8);

public static function
getCologneHash($word)
{
if (empty(
$word)) return false;
$len = strlen($word);

for (
$i = 0; $i < $len; $i++) {
$value[$i] = "";

//异常情况
if ($i == 0 && $word[$i] . $word[$i + 1] == "cr") {
$value[$i] = 4;
}

if (isset(
$word[$i + 1]) && isset(self::$eLeading[$word[$i] . $word[$i + 1]])) {
$value[$i] = self::$eLeading[$word[$i] . $word[$i + 1]];
}

if (
$i != 0 && (in_array($word[$i - 1] . $word[$i], self::$eFollow))) {
$value[$i] = 8;
}

// 正常编码
if ($value[$i]=="") {
if (isset(
self::$codingTable[$word[$i]])) {
$value[$i] = self::$codingTable[$word[$i]];
}
}
}

// 删除重复值
$len = count($value);

for (
$i = 1; $i < $len; $i++) {
if (
$value[$i] == $value[$i - 1]) {
$value[$i] = "";
}
}

// 删除元音
for ($i = 1; $i > $len; $i++) {
// 省略第一个字符代码和 h
if ($value[$i] == 0) {
$value[$i] = "";
}
}

$value = array_filter($value);
$value = implode("", $value);

return
$value;
}

}
?>
9
synnus at gmail dot com
9年前
<?php
// https://github.com/Fruneau/Fruneau.github.io/blob/master/assets/soundex_fr.php
// http://blog.mymind.fr/blog/2007/03/15/soundex-francais/
function soundex_fr($sIn){
static
$convVIn, $convVOut, $convGuIn, $convGuOut, $accents;
if (!isset(
$convGuIn)) {
$accents = array('É' => 'E', 'È' => 'E', 'Ë' => 'E', 'Ê' => 'E',
'Á' => 'A', 'À' => 'A', 'Ä' => 'A', 'Â' => 'A', 'Å' => 'A', 'Ã' => 'A',
'Ï' => 'I', 'Î' => 'I', 'Ì' => 'I', 'Í' => 'I',
'Ô' => 'O', 'Ö' => 'O', 'Ò' => 'O', 'Ó' => 'O', 'Õ' => 'O', 'Ø' => 'O',
'Ú' => 'U', 'Ù' => 'U', 'Û' => 'U', 'Ü' => 'U',
'Ç' => 'C', 'Ñ' => 'N', 'Ç' => 'S', '¿' => 'E',
'é' => 'e', 'è' => 'e', 'ë' => 'e', 'ê' => 'e',
'á' => 'a', 'à' => 'a', 'ä' => 'a', 'â' => 'a', 'å' => 'a', 'ã' => 'a',
'ï' => 'i', 'î' => 'i', 'ì' => 'i', 'í' => 'i',
'ô' => 'o', 'ö' => 'o', 'ò' => 'o', 'ó' => 'o', 'õ' => 'o', 'ø' => 'o',
'ú' => 'u', 'ù' => 'u', 'û' => 'u', 'ü' => 'u',
'ç' => 'c', 'ñ' => 'n');
$convGuIn = array( 'GUI', 'GUE', 'GA', 'GO', 'GU', 'SCI', 'SCE', 'SC', 'CA', 'CO',
'CU', 'QU', 'Q', 'CC', 'CK', 'G', 'ST', 'PH');
$convGuOut = array( 'KI', 'KE', 'KA', 'KO', 'K', 'SI', 'SE', 'SK', 'KA', 'KO',
'KU', 'K', 'K', 'K', 'K', 'J', 'T', 'F');
$convVIn = array( '/E?(AU)/', '/([EA])?[UI]([NM])([^EAIOUY]|$)/', '/[AE]O?[NM]([^AEIOUY]|$)/',
'/[EA][IY]([NM]?[^NM]|$)/', '/(^|[^OEUIA])(OEU|OE|EU)([^OEUIA]|$)/', '/OI/',
'/(ILLE?|I)/', '/O(U|W)/', '/O[NM]($|[^EAOUIY])/', '/(SC|S|C)H/',
'/([^AEIOUY1])[^AEIOUYLKTPNR]([UAO])([^AEIOUY])/', '/([^AEIOUY]|^)([AUO])[^AEIOUYLKTP]([^AEIOUY1])/', '/^KN/',
'/^PF/', '/C([^AEIOUY]|$)/', '/E(Z|R)$/',
'/C/', '/Z$/', '/(?<!^)Z+/', '/H/', '/W/');
$convVOut = array( 'O', '1\3', 'A\1',
'E\1', '\1E\3', 'O',
'Y', 'U', 'O\1', '9',
'\1\2\3', '\1\2\3', 'N',
'F', 'K\1', 'E',
'S', 'SE', 'S', '', 'V');
}

if (
$sIn === '' ) return ' ';
$sIn = strtr( $sIn, $accents);
$sIn = strtoupper( $sIn );
$sIn = preg_replace( '`[^A-Z]`', '', $sIn );
if (
strlen( $sIn ) === 1 ) return $sIn . ' ';
$sIn = str_replace( $convGuIn, $convGuOut, $sIn );
$sIn = preg_replace( '`(.)\1`', '$1', $sIn );
$sIn = preg_replace( $convVIn, $convVOut, $sIn);
$sIn = preg_replace( '`L?[TDX]?S?$`', '', $sIn );
$sIn = preg_replace( '`(?!^)Y([^AEOU]|$)`', '\1', $sIn);
$sIn = preg_replace( '`(?!^)[EA]`', '', $sIn);
return
substr( $sIn . ' ', 0, 4);
}
?>
4
cap at capsi dot cx
24年前
不幸的是,soundex() 对第一个字符非常敏感。它无法同时使用 Clansy 和 Klansy 返回相同的值。如果您想对这样的名字进行语音搜索,您仍然需要编写一个例程来评估 C452 是否与 K452 相似。
3
synnus at gmail dot com
4年前
<?php
/* SOUNDEX 法语
Frederic Bouchery 2003 年 9 月 26 日
http://www.php-help.net/sources-php/a.french.adapted.soundex.289.html
*/

function soundex2( $sIn ) {
// 如果没有词,立即退出
if ( $sIn === '' ) return ' ';
// 全部转为小写
$sIn = strtoupper( $sIn );
// 删除重音
$sIn = strtr( $sIn, 'ÂÄÀÇÈÉÊË&#338;ÎÏÔÖÙÛÜ', 'AAASEEEEEIIOOUUU' );
// 删除所有非字母字符
$sIn = preg_replace( '`[^A-Z]`', '', $sIn );
// 如果字符串只有一个字符,则退出。
if ( strlen( $sIn ) === 1 ) return $sIn . ' ';
// 替换主要辅音
$convIn = array( 'GUI', 'GUE', 'GA', 'GO', 'GU', 'CA', 'CO', 'CU',
'Q', 'CC', 'CK' );
$convOut = array( 'KI', 'KE', 'KA', 'KO', 'K', 'KA', 'KO', 'KU', 'K',
'K', 'K' );
$sIn = str_replace( $convIn, $convOut, $sIn );
// 替换所有元音,除了 Y 和第一个以外,都替换为 A
$sIn = preg_replace( '`(?<!^)[EIOU]`', 'A', $sIn );
// 替换前缀,然后保留第一个字母
// 并且进行补充替换
$convIn = array( '`^KN`', '`^(PH|PF)`', '`^MAC`', '`^SCH`', '`^ASA`',
'`(?<!^)KN`', '`(?<!^)(PH|PF)`', '`(?<!^)MAC`', '`(?<!^)SCH`',
'`(?<!^)ASA`' );
$convOut = array( 'NN', 'FF', 'MCC', 'SSS', 'AZA', 'NN', 'FF', 'MCC',
'SSS', 'AZA' );
$sIn = preg_replace( $convIn, $convOut, $sIn );
// 删除 H,除非是 CH 或 SH
$sIn = preg_replace( '`(?<![CS])H`', '', $sIn );
// 删除 Y,除非前面是 A
$sIn = preg_replace( '`(?<!A)Y`', '', $sIn );
// 删除 A、T、D、S 结尾
$sIn = preg_replace( '`[ATDS]$`', '', $sIn );
// 删除所有 A,除非在开头
$sIn = preg_replace( '`(?!^)A`', '', $sIn );
// 删除重复字母
$sIn = preg_replace( '`(.)\1`', '$1', $sIn );
// 只保留 4 个字符,或者用空格填充
return substr( $sIn . ' ', 0, 4);
}
?>
6
dcallaghan at linuxmail dot org
22 年前
虽然标准的 soundex 字符串是 4 个字符长,并且这是 php 函数返回的结果,但一些数据库程序返回任意数量的字符串。例如 MySQL。

MySQL 文档涵盖了这一点,建议您可能希望使用子字符串来输出标准的 4 个字符。以 'Dostoyevski' 为例。

select soundex("Dostoyevski")
返回 D2312
select substring(soundex("Dostoyevski"), 1, 4);
返回 D231

PHP 将返回值为 'D231'

因此,要使用 soundex 函数在 MySQL SELECT 语句中生成 WHERE 参数,您可以尝试以下方法
$s = soundex('Dostoyevski');
SELECT * FROM authors WHERE substring(soundex(lastname), 1 , 4) = "' . $s . '"';

或者,如果您想绕过 php 函数
$result = mysql_query("select soundex('Dostoyevski')");
$s = mysql_result($result, 0, 0);
4
witold4249 at rogers dot com
22 年前
一个 MUCH 更容易的方法来检查单词之间的相似性,并避免 Klancy/Clancy 出现的问题,是在字符串前面添加任何字母

例如:OKlancy/OClancy
4
administrator at zinious dot com
22 年前
我很久以前用 CGI-perl 写了这个函数,然后翻译(如果你能称之为这样)成 PHP。说真的,有点笨拙,但应该能 100% 满足真正的 soundex 规范。

// --- 代码开始 ---

function MakeSoundEx($stringtomakesoundexof)
{
$temp_Name = $stringtomakesoundexof;
$SoundKey1 = "BPFV";
$SoundKey2 = "CSKGJQXZ";
$SoundKey3 = "DT";
$SoundKey4 = "L";
$SoundKey5 = "MN";
$SoundKey6 = "R";
$SoundKey7 = "AEHIOUWY";

$temp_Name = strtoupper($temp_Name);
$temp_Last = "";
$temp_Soundex = substr($temp_Name, 0, 1);

$n = 1;
for ($i = 0; $i < strlen($SoundKey1); $i++)
{
if ($temp_Soundex == substr($SoundKey1, i - 1, 1))
{
$temp_Last = "1";
}
}
for ($i = 0; $i < strlen($SoundKey2); $i++)
{
if ($temp_Soundex == substr($SoundKey2, i - 1, 1))
{
$temp_Last = "2";
}
}
for ($i = 0; $i < strlen($SoundKey3); $i++)
{
if ($temp_Soundex == substr($SoundKey3, i - 1, 1))
{
$temp_Last = "3";
}
}
for ($i = 0; $i < strlen($SoundKey4); $i++)
{
if ($temp_Soundex == substr($SoundKey4, i - 1, 1))
{
$temp_Last = "4";
}
}
for ($i = 0; $i < strlen($SoundKey5); $i++)
{
if ($temp_Soundex == substr($SoundKey5, i - 1, 1))
{
$temp_Last = "5";
}
}
for ($i = 0; $i < strlen($SoundKey6); $i++)
{
if ($temp_Soundex == substr($SoundKey6, i - 1, 1))
{
$temp_Last = "6";
}
}
for ($i = 0; $i < strlen($SoundKey6); $i++)
{
if ($temp_Soundex == substr($SoundKey6, i - 1, 1))
{
$temp_Last = "";
}
}

for ($n = 1; $n < strlen($temp_Name); $n++)
{
if (strlen($temp_Soundex) < 4)
{
for ($i = 0; $i < strlen($SoundKey1); $i++)
{
if (substr($temp_Name, $n - 1, 1) == substr($SoundKey1, $i - 1, 1) && $temp_Last != "1")
{
$temp_Soundex = $temp_Soundex."1";
$temp_Last = "1";
}
}
for ($i = 0; $i < strlen($SoundKey2); $i++)
{
if (substr($temp_Name, $n - 1, 1) == substr($SoundKey2, $i - 1, 1) && $temp_Last != "2")
{
$temp_Soundex = $temp_Soundex."2";
$temp_Last = "2";
}
}
for ($i = 0; $i < strlen($SoundKey3); $i++)
{
if (substr($temp_Name, $n - 1, 1) == substr($SoundKey3, $i - 1, 1) && $temp_Last != "3")
{
$temp_Soundex = $temp_Soundex."3";
$temp_Last = "3";
}
}
for ($i = 0; $i < strlen($SoundKey4); $i++)
{
if (substr($temp_Name, $n - 1, 1) == substr($SoundKey4, $i - 1, 1) && $temp_Last != "4")
{
$temp_Soundex = $temp_Soundex."4";
$temp_Last = "4";
}
}
for ($i = 0; $i < strlen($SoundKey5); $i++)
{
if (substr($temp_Name, $n - 1, 1) == substr($SoundKey5, $i - 1, 1) && $temp_Last != "5")
{
$temp_Soundex = $temp_Soundex."5";
$temp_Last = "5";
}
}
for ($i = 0; $i < strlen($SoundKey6); $i++)
{
if (substr($temp_Name, $n - 1, 1) == substr($SoundKey6, $i - 1, 1) && $temp_Last != "6")
{
$temp_Soundex = $temp_Soundex."6";
$temp_Last = "6";
}
}
for ($i = 0; $i < strlen($SoundKey7); $i++)
{
if (substr($temp_Name, $n - 1, 1) == substr($SoundKey7, $i - 1, 1))
{
$temp_Last = "";
}
}
}
}

while (strlen($temp_Soundex) < 4)
{
$temp_Soundex = $temp_Soundex."0";
}

return $temp_Soundex;
}

// --- 代码结束 ---
3
justin at NO dot blukrew dot SPAM dot com
19 年前
我最初查看 soundex() 是因为我想比较各个字母的发音。因此,当发音一串生成的字符时,很容易将它们彼此区分开(例如,TGDE 很难区分,而 RFQA 更容易理解)。目标是生成 ID,这些 ID 可以在质量不同的无线电中以高精度轻松理解。我很快发现 soundex 和 metaphone 做不到这一点(它们适用于单词),所以我写了以下内容来帮忙。ID 生成函数迭代地调用 chrSoundAlike() 来比较每个新字符与前一个字符。我很乐意收到对此的任何反馈。谢谢。

<?php
function chrSoundAlike($char1, $char2, $opts = FALSE) {
$char1 = strtoupper($char1);
$char2 = strtoupper($char2);
$opts = strtoupper($opts);

// 设置发音相似的字符集。
// (选项:包含数字,包含 W,包含两者,或默认不包含任何这些选项。)
switch ($opts) {
case
'NUMBERS':
$sets = array(0 => array('A', 'J', 'K'),
1 => array('B', 'C', 'D', 'E', 'G', 'P', 'T', 'V', 'Z', '3'),
2 => array('F', 'S', 'X'),
3 => array('I', 'Y'),
4 => array('M', 'N'),
5 => array('Q', 'U', 'W'));
break;

case
'STRICT':
$sets = array(0 => array('A', 'J', 'K'),
1 => array('B', 'C', 'D', 'E', 'G', 'P', 'T', 'V', 'Z'),
2 => array('F', 'S', 'X'),
3 => array('I', 'Y'),
4 => array('M', 'N'),
5 => array('Q', 'U', 'W'));
break;

case
'BOTH':
$sets = array(0 => array('A', 'J', 'K'),
1 => array('B', 'C', 'D', 'E', 'G', 'P', 'T', 'V', 'Z', '3'),
2 => array('F', 'S', 'X'),
3 => array('I', 'Y'),
4 => array('M', 'N'),
5 => array('Q', 'U', 'W'));
break;

default:
$sets = array(0 => array('A', 'J', 'K'),
1 => array('B', 'C', 'D', 'E', 'G', 'P', 'T', 'V', 'Z'),
2 => array('F', 'S', 'X'),
3 => array('I', 'Y'),
4 => array('M', 'N'),
5 => array('Q', 'U'));
break;
}

// 查看 $char1 是否在某个集合中。
$matchset = array();
for (
$i = 0; $i < count($sets); $i++) {
if (
in_array($char1, $sets[$i])) {
$matchset = $sets[$i];
}
}

// 如果 $char2 与 $char1 在同一个集合中,或者 $char1 和 $char2 相同,则返回 true。
if (in_array($char2, $matchset) OR $char1 == $char2) {
return
TRUE;
} else {
return
FALSE;
}
}
?>
3
fie at myrealbox dot com
21 年前
嗯... 那台服务器上的托管服务被关闭了.. 这是之前代码的代码

function cg_sylc($nos){
$nos = strtoupper($nos);
$syllables = 0;

$before = strlen($nos);
$nos = str_replace(array('AA','AE','AI','AO','AU',
'EA','EE','EI','EO','EU','IA','IE','II','IO',
'IU','OA','OE','OI','OO','OU','UA','UE',
'UI','UO','UU'), "", $nos);
$after = strlen($nos);
$diference = $before - $after;
if($before != $after) $syllables += $diference / 2;

if($nos[strlen($nos)-1] == "E") $syllables --;
if($nos[strlen($nos)-1] == "Y") $syllables ++;

$before = $after;
$nos = str_replace(array('A','E','I','O','U'),"",$nos);
$after = strlen($nos);
$syllables += ($before - $after);

return $syllables;
}

function cg_SoundEx($SExStr){
$syl = cg_sylc($SExStr);
$SExStr = strtoupper($SExStr);

for($i = 1, $ii = 2,print $SExStr[0]; ;$ii++){

if(($SExStr[$i] != $SExStr[$ii])){
$tsstr .= $SExStr[$ii];
$i ++;
}
if($SExStr[$ii] == false){
break;
}
}

$tsstr = str_replace(array('A', 'E', 'H', 'I', 'O', 'U', 'W', 'Y'), "", $tsstr);
$tsstr = str_replace(array('B', 'F', 'P', 'V'), "1", $tsstr);
$tsstr = str_replace(array('C', 'G', 'J', 'K', 'Q', 'S', 'X', 'Z', '?'), "2", $tsstr);
$tsstr = str_replace(array('D', 'T'), "3", $tsstr);
$tsstr = str_replace(array('L'), "4", $tsstr);
$tsstr = str_replace(array('M', 'N', '?'), "5", $tsstr);
$tsstr = str_replace(array('R'), "6", $tsstr);

while($iii < 3){
if($tsstr[$iii] != false){
$ttsstr .= $tsstr[$iii];
} else {
$ttsstr .= "0";
}
$iii ++;
}
$ttsstr .= $syl;
print $ttsstr;
}
1
mail at gettheeawayspam dot iaindooley dot com
21 年前
Soundex 的“前面不同的字母”问题可以通过对 Soundex 代码使用 levenshtein() 来解决。在我的应用程序中,它是在专辑名称数据库中搜索与用户提供的特定字符串匹配的条目,我执行以下操作

1. 在数据库中搜索完全相同的名称
2. 在数据库中搜索名称以任何方式作为字符串出现的条目
3. 在数据库中搜索名称中任何单词(如果用户输入了多个单词)存在的条目,但小词(and、the、of 等)除外
4. 然后,如果所有这些都失败,我转到计划 B

- 计算用户搜索词与数据库中每个条目之间的 Levenshtein 距离 (levenshtein()),以用户输入的搜索词的长度为百分比

- 计算用户输入的搜索词的元音代码与数据库中每个字段之间的 Levenshtein 距离,以用户输入的搜索词的元音代码的长度为百分比

- 计算用户输入的搜索词的 Soundex 代码与数据库中每个字段之间的 Levenshtein 距离,以原始用户输入的搜索词的 Soundex 代码的长度为百分比

如果这些百分比中的任何一个小于 50(意味着将接受具有不同首字母的两个 Soundex 代码!!),则该条目将被接受为可能的匹配项。
3
Anonymous
22 年前
执行上述搜索的一个简单得多的方法是简单地在字符串前面添加任何字母,然后进行比较。

即。Klancy => LKlancy
Clancy => LClancy
1
Anonymous
18 年前
由于第一个字母包含在输出中的语音表示中,因此值得指出,如果您希望 Soundex 键在没有 klansy 和 clansy 听起来不同的问题的情况下工作,请从第一个字母开始取子字符串,因为第一个字母是单词的主要常数,数字值是单词的语音结构。
0
crchafer-php at c2se dot com
18 年前
重写了,也许吧 - 但是算法有一些明显的
优化可以进行,例如...

function text__soundex( $text ) {
$k = ' 123 12 22455 12623 1 2 2';
$nl = strlen( $tN = strtoupper( $text ) );
$p = trim( $k{ ord( $tS = $tN{0} ) - 65 } );
for( $n = 1; $n < $nl; ++$n )
if( ( $l = trim( $k{ ord( $tN{ $n } ) - 65 } ) ) != $p )
$tS .= ( $p = $l );
return substr( $tS . '000', 0, 4 );
}

// 注释
// $k 是 $key,本质上是 $SoundKey 的反转
// $tN 是要优化的文本的大写
// $tS 是部分生成的输出
// $l 是当前字母,$p 是前一个
// $n 和 $nl 是迭代索引
// 65 是 ord('A'),预先计算以提高速度
// 不支持非 ASCII 字母
// 注意括号,这里混合了很多

(代码只经过了基本测试,虽然看起来
与 PHP 的 soundex() 的输出匹配,速度未经测试 -
虽然这应该比 a4_perfect 的
重写速度快很多,因为去掉了大部分循环和比较。)

C
2005-09-13
0
Marc Quinton.
19 年前
一个法语 soundex 版本;可以用于其他 soundex 不支持的外国语言。也许可以编写一个包含每种语言特性的类。

http://www.php-help.net/sources-php/a.french.adapted.soundex.289.html
0
pee whitt at dental dot ufl dor edu
21 年前
fie at myrealbox dot com-

关于你的 soudex 音节请求 - 我认为计算单词中的元音簇会得到准确的音节数。因此不需要 soudex 功能,只需遍历单词中的字符,每当你从元音到辅音时,就增加音节计数。

使用这种逻辑,这句话被归类如下。
2 1 2 1 1 (3) (0) (4) (0) 2

其中 (#) 标记了一个被错误分类的单词。我确信用一点思考就可以找出这些情况下会导致准确计数的逻辑。计算元音到辅音的变化将产生 -
(1) 1 2 1 2 1 (4) 1 2

取这两种类型的平均值,然后对结果向上取整,可以修正大部分错误。
-1
shortcut
17 年前
关于 soundex 是否除了第一个字母之外都适用于 klancy 和 clancy 的答案是,始终在单词前加相同的字母。

aklancy 将匹配 aclancy
bklancy 将匹配 bclancy

soundex 似乎只检查前 2 个音节。??
例如:spectacular 匹配 spectacle

如果你依赖 soundex,这只是一个想法。

k-
-1
jr
21 年前
解决 mysql/php 在 soundex 实现上的差异的一种方法是在 mysql 中完全进行 soundex 比较。

例如
$sql = "SELECT * FROM table WHERE substring(soundex(field), 1, 4) = substring(soundex('".$wordsearch."'), 1, 4)";
-1
info at nederlandsch dot net
21 年前
MySQL soundex (3.23.49) 根本不检查第一个字符,以查看是否应该跳过它。因此,荷兰的首都海牙的名称 's-Gravenhage 在 MySQL 中的 soundex 值为 '261,而在 PHP 中为 S615。
To Top