web-dev-qa-db-ja.com

余分な文字を含む同じ文字列のレコードを検索する

さて、私はownerというMicrosoft SQL Server 2014データベーステーブルを持っています。所有者情報を含む約90,000件のレコードがあり、別のvehicleという名前が車両情報を持っています

Owner_Name                   owner_id       V_name     owner_id    exempt
-------------------------------------       ------------------------------
JACOB JAMISON & JESSICA           35        Civic            35        H3
JACOB JAMISON M & JESSICA B       39        Accord           39        H3 
BLACKSON BARRINGTON               56        Bugatti          56        H6
BLACKSON BARRINGTON H             98        SSC              98        H7
BRUSTER MICHAEL                   107       Corvette         107       H9

車両で複数の免除があるすべてのレコードを検索しようとしています(H0は免除がないことを意味します)。以下のこのコードはうまくいきました名前が完全に同じである限り。ただし、余分な文字などのバリエーションがある場合、または逆方向に入力された場合、それらのレコードは返されません。私はSOUNDEXのようなものを見てきましたが、これは私のシナリオでは機能しません。

SELECT Owner_name
     , COUNT(Owner_name) AS 'xNameAppears'
     , COUNT(v.exempt) AS 'ExemptionCount' 
FROM owner o
INNER JOIN vehicle V ON V.owner_id = o.owner_id
WHERE v.exempt <> 'H0'
GROUP BY O.owner_name
HAVING COUNT(v.exempt) > 1

どのowner_nameが似ているかわからないようなレコードを返すことができる解決策はありますか?基本的に、サーバーにowner_name列を検索させようとし、JACOB JAMISON & JESSICAJACOB JAMISON M & JESSICA Bなどの類似点がある場合、それらのレコードを次のように返します。

Owner_Name                      xNameAppears      ExemptCount
-------------------------------------------------------------      
JACOB JAMISON & JESSICA           2                         2
JACOB JAMISON M & JESSICA B       2                         2
BLACKSON BARRINGTON               2                         2
BLACKSON BARRINGTON H             2                         2

前もって感謝します!

3
MindXpert

[〜#〜] soundex [〜#〜] 関数は列にも適用できます。

しかしそれ以来

そのような何千ものがあります

それを行うために関数に結合するクエリを記述するだけではお勧めしません。

これは、大きなテーブルではあまりうまく機能しない可能性があります。

SELECT *
FROM dbo.vehicle AS v
JOIN dbo.vehicle AS v2
ON SOUNDEX(v2.Owner_Name) = SOUNDEX(v.Owner_Name)
AND v2.Owner_Name <> v.Owner_Name;

これを長期的に見つけやすくするようなことをしたいのですが。

次に例を示します。

CREATE TABLE dbo.vehicle (Owner_Name VARCHAR(50));
INSERT dbo.vehicle ( Owner_Name )
SELECT *
FROM (  
VALUES            
('JACOB JAMISON & JESSICA'),
('JACOB JAMISON M & JESSICA B'),
('BLACKSON BARRINGTON'),          
('BLACKSON BARRINGTON H'),        
('BRUSTER MICHAEL')
) AS x (Owner_Name);

関数に基づいて 計算列 を追加し、クエリを支援するためにインデックスを追加します。

ALTER TABLE dbo.vehicle ADD Owner_Soundex AS SOUNDEX(Owner_Name);

CREATE INDEX ix_whatever ON dbo.vehicle (Owner_Soundex, Owner_Name);

すべてが適切に見えることを検証します...

SELECT *
FROM dbo.vehicle AS v

次のようなクエリを使用して、不正確な一致を見つけます。

SELECT *
FROM dbo.vehicle AS v
JOIN dbo.vehicle AS v2
ON v2.Owner_Soundex = v.Owner_Soundex
AND v2.Owner_Name <> v.Owner_Name;
5
Erik Darling