实现音素搜索的最有效方法

18

如何在C++和/或Java中实现最有效的音标搜索?所谓的音标搜索是指替换听起来相似的元音或辅音。这对于姓名尤其有用,因为有时人们的名字拼写很奇怪。

我认为将元音和一些辅音进行替换可能是有效的。还可以包括一些特殊情况,例如末尾的无声E或F和PH。在C++中是使用cstrings还是strings更好?是否最好在内存中存储带有替换值的副本,还是每次查找时调用函数?

2个回答

23
除了 Soundex,您还可以找到 Metaphone 或 Double Metaphone 这些音标算法。它们似乎是对英语发音的改进,并且是一个相当新的算法。 对于德语发音,我使用 "Kölner Phonetik"。 Apache Commons Codec 提供了这些基本算法(Soundex、Metaphone 等)的非常简单的 Java 实现。 http://commons.apache.org/codec/ 例如,请参阅 Soundex 的 javadoc: http://commons.apache.org/codec/apidocs/org/apache/commons/codec/language/Soundex.html 只需键入以下代码,即可获得字符串的音标值:
Soundex soundex = new Soundex();
String phoneticValue = soundex.encode("YourString");
然后,您可以针对两个字符串执行此操作并比较它们的语音值。 如果您正在比较两个字符串,那么请查看以下帖子,因为equals()方法只是非常明确的黑白,也许您想知道它匹配了多少%: 如何在Java中比较几乎相似的字符串?(字符串距离测量)

你知道“科隆音标”在JAVA中的实现吗? - mica
1
是的 - 我们使用了Apache Commons Codec。在这里,您可以找到“ColognePhonetic”类。'new ColognePhonetic().encode("Hans")'。但是我们不再将其用于德语,因为它似乎忽略了太多内容,几乎所有单词都被视为相等。 - Philipp
2
对于德语,我找到了汉诺威音标,一个Java实现的Phonet4Java,可以在这里找到:http://code.google.com/p/phonet4java - mica

15

Soundex 及其变体是用于此目的的标准算法。它使用语音规则将名称转换为字母数字代码。具有相同代码的名称被分组在一起。

关于实现搜索,我会使用一个数据结构,将每个 Soundex 代码映射到具有该代码的名称列表。根据所使用的数据结构(哈希表或树),查找可以在恒定时间或对数时间内完成,取决于不同 Soundex 代码的数量。

我不确定您所说的cstring 是什么意思(Microsoft 的 CString?),但标准的 std::string 类对于这个问题来说完全可以胜任,并且是我的首选。


我所说的“cstring”是指类型为“char”的数组。 - ctype.h
1
@user964672:在这里没有理由这样做——我的建议是坚持使用std::string - NPE

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,