2016-08-05 14 views
0

私はUとVのアドレスを持っています。私はそれらが幾分似ているかどうか、 "更新"と言いたいのですか?2つのアドレス欄を比較する

たとえば、Uの246 N High streetとVの246 North High Stは、Updateの値を返します。 Uの 246 N High StreetとVの458 Auburn Driveは、Omitの値を返します。

アイデア?

+1

これは一般的に難しい問題です。何らかのファジーマッチングを使用する必要があります。それについてどうすればいいのかについての解答[ここ](http://stackoverflow.com/questions/14821345/excel-approximate-text-match)をご覧ください。 –

答えて

0

ファジーマッチングを行うアルゴリズムはたくさんあります。優れた実装方法の1つはN-Gramです。

nグラム一致を実行するには、各アドレスを小さな文字長のセットのリストに分割する必要があります。あなたの住所246 N High streetの2グラムのリストは、24,46,6 , N,N , H,Hi,ig,gh,h , s,st,tr,re,ee,etのようになります。 246,46 ,6 N, N ,N H, Hi,Hig,igh,gh ,h s, st,str,tre,ree,eet

これを両方のアドレスで行い、最初のアドレスのリストの各項目をチェックして、2番目のアドレスのリストに表示されているかどうかを調べることができます。一致を数え、最初のリストの項目数で除算します。それは彼らがどれほど近づいているかのパーセンテージを与えます。

シート式でこれを行うには、セル式mid()countif()が好きかもしれませんが、VBAで書き出してUDFにする方が簡単だと思います。

Function NGramCompare(string1 As String, string2 As String, intGram As Integer) As Double 
    'Take in two strings and the N-gram 
    Dim intChar As Integer, intGramMatch As Integer 
    Dim ngramList1 As String, ngramList2 As String, nGram As Variant 
    Dim nGramArr1 As Variant 

    'split the first string into a list of ngrams   
    For intChar = 1 To Len(string1) - (intGram-1) 
     If ngramList1 <> "" Then ngramList1 = ngramList1 & "," 
     ngramList1 = ngramList1 & Mid(string1, intChar, intGram) 
    Next intChar 

    'split the secong string into a list of ngrams   
    For intChar = 1 To Len(string2) - (intGram-1) 
     If ngramList2 <> "" Then ngramList2 = ngramList2 & "," 
     ngramList2 = ngramList2 & Mid(string2, intChar, intGram) 
    Next intChar 

    'Split the ngramlist1 into an array through which we can iterate 
    nGramArr1 = Split(ngramList1, ",") 

    'Iterate through array and compare values to ngramlist2 
    For Each nGram In nGramArr1 
     If InStr(1, ngramList2, nGram) Then 
      'we found a match, add to the counter 
      intGramMatch = intGramMatch + 1 
     End If 
    Next nGram 

    'output the percentage of grams matching. 
    NGramCompare = intGramMatch/(UBound(nGramArr1) + 1) 
End Function 

あなたはUDFを使用したことがない場合:ブックを見つけ、VBAプロジェクトウィンドウでAltキー+ F11

  • でVisual Basicエディター(VBE)に

    1. 移動して、右クリックしました名前
    2. 選択:挿入>>モジュールを
    3. ダブル
    4. それのコードウィンドウを開き、リストに新しいモジュールをクリックして、この機能を貼り付け、ワークブック保存

    次に、アドレス1と仮定するとA1にあり、アドレス2は、あなたがC1に、置くことができるB1である:

    =NGramCompare(A1, B1, 2) 
    

    どの、あなたの最初のアドレスのために、56%を吐き出すます。それは合理的に良い試合のように思える。ポジティブヒットが多すぎる場合は、最後のパラメータを変更して2グラムを3グラムに変更することができます。

    =If(NGramCompare(A1, B1, 2)>.30, "Update", "Omit") 
    

    私はちょうどそれが30%以上の一致何かを検討するようにすることを設定しています:それはあなたができる「更新」または「省略」と言うだろうさらに一歩それを取るために

    必要に応じて調整することができます。どこに設定しても、誤検知や偽のネガティブな割合の比較が行われることになりますが、これがファジーマッチングの方法です。

  • +0

    の前にすべてを取得するのは大変です、ありがとう! – Ryan

    +0

    これは素晴らしいです、私はそれを入れて、それはすぐに働いた!本当にありがとう!! – Ryan

    +0

    確かです。私は過去数回、この問題にぶつかってきましたが、最近までそれを解決する知識は不足していました。 Web上に似たような機能がないのに驚いていますが、私はこれまでに一度も実行していません。 – JNevill

    0

    ナイーブなアプローチのいくつかは、最初の数文字

    =LEFT(A1,5)=LEFT(B1,5) 
    

    を比較するか、彼らはおそらくのために調整した後、大きな醜い式に変わります

    =(SUBSTITUTE(SUBSTITUTE(LOWER(A2)," street"," ST")," north "," N ") 
    =SUBSTITUTE(SUBSTITUTE(LOWER(B2)," street"," ST")," north "," N ")) 
    

    両方に一致するまで、部品を交換することができますほとんどの場合

    +0

    That = Leftはうまくいくはずですが、最初の数桁を見て、一致するかどうかを調べることができます。ありがとうございました – Ryan

    +0

    '= LEFT(A1、FIND(" "、A1) - 1)' – Slai