【问题标题】:Data cleansing - how to decide which names are misspellings or are equivalent but slightly different?数据清理 - 如何确定哪些名称是拼写错误或相同但略有不同?
【发布时间】:2013-09-20 10:36:01
【问题描述】:

我们有一个包含公司名称和数字主键标识的表。我们正在清理数据,我们发现名称列中充满了代表同一家公司的相似名称。

例如BA 和 Ba 或 GTC Ltd 和 GTC Limited。

无论如何,我们是否可以使用 SQL Server 获得具有相似名称和 ID 列表的所有项目的计数和摘要。我想知道是否有某种相似性比较,我们可以为 etc 设置阈值

我们需要向客户提供一个看起来需要合并的名称列表。

【问题讨论】:

    标签: sql sql-server data-analysis data-cleaning


    【解决方案1】:

    基本答案是“不”。正名是个难题。像“GTC Ltd”和“GTC Limited”这样的两个名称比“GTC”和“GTE”(通过更明显的衡量标准)更加不同。为此目的有外部服务局和专用软件。

    如果您正在处理少量数据,我建议您将值按字母顺序排列,将它们加载到 Excel 中,然后在 Excel 中添加一个带有“官方”名称的列。然后,您可以将其重新导入为数据库中的表以执行您想要的操作。如果您删除已知的后缀和前缀,例如“ltd”、“bros”、“partners”等,可能会有所帮助。

    如果您确实尝试走类似soundex() 的道路,那么请确保您选择understand it well。例如,以下两个字符串的soundex() 值是相同的:“gte, blah blah blah”和“gdteey, junk goes here”。

    【讨论】:

    • 谢谢。是的,我可能会看类似谷歌细化而不是 SQL Server 的东西,它实际上并没有对这个问题提供任何内置支持
    【解决方案2】:

    有很多功能可以检查相似之处。 MS SQL 提供了SOUNDEXDIFFERENCE 函数,我从未真正使用过。

    虽然我曾经在 PHP 中使用过Levenshtein(将 string1 转换为 string2 的最小编辑),但它非常有效。这是 Devio's implementation in TSQL 作为一个函数,您可以将其放入您的代码中:

    SELECT 
        LEVENSHTEIN(COL1, COL2) 
    FROM 
        ExampleTable
    

    或者在WHERE条件下:

    SELECT 
        COL1, COL2
    FROM
        ExampleTable
    WHERE
        LEVENSHTEIN(COL1, COL2) < 5
    

    在这里,我建议您实现一些 CASE - WHEN - THEN 逻辑,以找到适合您需要的正确 levenshtein 距离。

    【讨论】:

    • 知道如何将其应用于整个表格以生成相似名称的摘要列表吗?我只有一个表,所以我需要比较所有名称并生成我猜想的相似名称列表。猜测交叉连接并将它们相互比较
    • 将此与 gvee 答案相结合,但它并没有真正给出很好的结果。也许如果我删除所有 Ltd/limited 等,它会更接近。可能还有很多只是它认为非常相似但并不相似的首字母
    • @GraemeMiller - 您可以将其与字典表结合起来,以获得缩写和全名
    【解决方案3】:

    您的答案在于SoundEx()Difference() 函数。

    DECLARE @a varchar(50) = 'BA'
          , @b varchar(50) = 'Ba'
    ;
    
    SELECT @a
         , @b
         , SoundEx(@a)
         , SoundEx(@b)
         , Difference(@a, @b)
    ;
    
    SET @a = 'GTC Ltd';
    SET @b = 'GTC Limited';
    
    SELECT @a
         , @b
         , SoundEx(@a)
         , SoundEx(@b)
         , Difference(@a, @b)
    ;
    
    SET @a = 'BLAH';
    
    SELECT @a
         , @b
         , SoundEx(@a)
         , SoundEx(@b)
         , Difference(@a, @b)
    ;
    

    SoundEx“听起来像” - 这是一个返回输入表示的函数,您可以将其与其他输出进行比较。

    Difference() 函数返回一个介于 0 和 4 之间的值,其中数字越大表示匹配越好。

    【讨论】:

    • 知道如何将其应用于整个表格以生成相似名称的摘要列表吗?
    • 在技术上看起来很棒 - 但实际上它产生了 3338 行,其中 4 行不同。只有 1686 家公司,所以不确定 SQL 服务器功能是否能胜任
    • 与 LEVENSHTEIN 结合,这看起来更有希望
    • @GraemeMiller 查询执行CROSS 连接,生成笛卡尔积。这样我们就可以将每一行与其他行进行比较。然后我们根据唯一键对其进行过滤,以便我们只比较每个组合一次(即仅a=bb=a 之一)并排除自我比较,因为&lt; 不包含等号运算符(即没有a=a)。最后,我们只检索具有高(4 是返回的最高值)相似度的那些。我看不到您的数据,但如果您遵循这些规则,您的结果应该是正确
    • @GraemeMiller 您还可以添加到WHERE 子句:x1.val &lt;&gt; x2.val 以排除完全匹配。
    【解决方案4】:

    您可以使用 COLLATE UTF8_GENERAL_CILIKE 运算符来检查 BA and Ba 。 但是对于GTC Ltd and GTC Limited,您仍然可以使用相同的,但是您应该手动检查它们并仔细合并。

    【讨论】:

      猜你喜欢
      • 2020-07-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-03-08
      • 1970-01-01
      • 1970-01-01
      • 2023-03-14
      • 2010-11-25
      相关资源
      最近更新 更多