0

背景:我有一个庞大的人员数据库,我想查找重复项,这比看起来要困难得多。我已经对名字(通常以不同的方式拼写)、出生日期等进行了很多比较。当两个配置文件看起来与匹配算法足够相似时,它们会被呈现给将要判断的操作员。

大多数个人资料都附有多个电话号码,所以我想用它们来查找重复项。它们可以输入为“001-555-123456”,也可以输入为“555-123456”、“555-123456-7-8”、“555-123456 晚上给我打电话”或任何您可能想象的。我的第一个想法是去除所有非数字字符并获得“最长的公共子字符串”。有很多算法可以找到集合中最长的公共子串。但是每当我比较两个配置文件 A 和 B 时,我都有两组电话号码。我想找到集合 A 中的字符串和集合 B 中的字符串之间的最长公共子字符串。你能帮我找到这样的算法吗?我通常用 PHP 编程,只有 SQL 的解决方案会更好,但任何其他语言都可以。

4

2 回答 2

1

正如 Voitcus 之前所说,在开始比较或查找重复数据之前,您必须先清理数据。电话号码应遵循严格的模式。对于与模式不匹配的数字,请尝试对其进行调整。然后您就可以查找重复项。

此外,您应该在持久化之前进行数据清理,也许在单独的列中。然后,您在查找重复项时不必关心它......只是为了避免性能峰值。

像 php 中的 levenshtein 或similar_text() 这样的算法,不太适合该用例。

于 2013-05-16T12:19:20.513 回答
0

在我看来,最好的方法是从包含电话号码的文本中删除所有非数字字符。您可以通过多种方式做到这一点,一些正则表达式是最好的,但请参见下文。

然后,如果可能的话,你可以找到国家方向代码,如果用户有它的位置国家。如果没有,则假定为默认值并添加到字符串中。城市可能也是如此。您也可以尝试查看一个人的生活,他们的邮政编码等。

最后,您应该拥有可以轻松比较的统一电话号码。

另一种方法是将字符串与删除的国家(和城市)代码进行比较。

关于搜索“最长的公共子字符串”:因此过滤的数字是相同的,但是您可能需要它,例如。如果有人输入“下午 6 点后给我打电话”。如果您确定电话号码始终位于开头,因此没有人输入类似 555-SUPERMAN 的内容(转换为 555-78737626),则还可以删除最后一个字母数字字符(以及此字符)之后的所有内容.

还可以在 SQL 语句中过滤此类数据。考虑类似SELECT ..., [your trimming function(phone_number)] AS trimmed_phone WHERE (trimmed_phone is not numerical characters only) GROUP BY trimmed_phone. 如果修剪功能只删除空格和特殊分隔符,例如, -(通常在德国使用),也许等等,这个查询会留下所有被修剪但包含非数字字符的电话号码 - 看看结果,可能主要是数字和字母。他们有多少人?也许他们有共同点?也许您也可以过滤掉一些典型的短语?+.,

如果此类查询的结果不是很多,那么手动进行可能更容易?

于 2013-05-16T12:05:20.430 回答