2017-11-26 7 views
0

トランザクションが行われたベンダーの名前を収集するPandasデータフレームがあります。このデータは銀行の明細書から自動的に収集されるため、多くのベンダーが類似していますが、全く同じではありません。要約すると、ベンダーの名前の異なる順列を単一の名前に置き換えたいと考えています。同様の文字列を同じ文字列で置き換えます。

私はそれを行う方法を考えることができます(下記参照)が、私は初心者であり、これは複雑な問題のようです。私は本当に経験豊富なコーダーがそれにどのようにアプローチするかを知りたいと思っています。私はこのようなデータフレーム

(実際の生活の中で、それは約20の列と約50行の最大だ)している:

 Groceries   Car    Luxuries 
0 Sainsburys   Texaco wst453  Amazon 
1 Sainsburys bur  Texaco east  Firebox Ltd 
2 Sainsbury's east  Shell wstl   Sony 
3 Tesco    Shell p/stn  Sony ent nrk 
4 Tescos ref 657  Texac    Amazon EU 
5 Tesco 45783   Moto    Amazon marketplace 

私は類似したエントリを検索し、最初に置き換えるしたいのですがこれらのエントリの例ですので、私はこれで終わるでしょう:

 Groceries   Car    Luxuries 
0 Sainsburys   Texaco wst453  Amazon 
1 Sainsburys   Texaco wst453  Firebox Ltd 
2 Sainsburys   Shell wstl   Sony 
3 Tesco    Shell wstl   Sony 
4 Tesco    Texaco wst453  Amazon 
5 Tesco    Moto    Amazon 

私の解決策は最適ではないかもしれません。私はアルファベット順に並べ替えることを考えていましたが、bitwiseを使ってdifflibのSequenceMatcherのようなものを使って各ベンダーを比較しました。類似度があるパーセンテージ以上であれば(私が満足するまでこの値で遊ぶことを期待しています)、2つのベンダーは同じとみなされます。私はナットを裂くためにスレッジハンマーを使用しているかもしれないことに懸念しています。あるいは、長い時間がかかるかもしれません(私はパフォーマンスに執着していませんが、同様に私は結果を待っていません)。

この問題に関する人々の考えを本当に興味があります!

+0

私はあなたが同じ名前を持つ必要があるすべてのレコードで最初の単語が同じであれば簡単かもしれないと思います。 'Tesco'を使うのではなく' Tesco'しかありません。さもなければ、類似性を調べる必要があります。 – 0p3n5ourcE

+0

ええ、最初の単語は必ずしも同じではありません。残念ながら、何らかの点で類似性のチェックが必要なようです。 – user4896331

答えて

0

最初は、問題は複雑ではないようですが、それはあります。私は自分のコードが気に入らず、より良い方法が必要です。しかし、私のコードは動作しています。

fuzzywuzzyという名前の文字列類似性パッケージを使用して、置き換える文字列を決定しました。このパッケージはLevenshtein Similarityを使用しており、しきい値として%90を使用しました。また、任意の文字列の最初の単語が比較文字列として使用されます。ここに私のコードは次のとおりです。

import pandas 
from fuzzywuzzy import fuzz 

# Replaces %90 and more similar strings 
def func(input_list): 
    for count, item in enumerate(input_list): 
     rest_of_input_list = input_list[:count] + input_list[count + 1:] 
     new_list = [] 
     for other_item in rest_of_input_list: 
      similarity = fuzz.ratio(item, other_item) 
      if similarity >= 90: 
       new_list.append(item) 
      else: 
       new_list.append(other_item) 
     input_list = new_list[:count] + [item] + new_list[count :] 

    return input_list 

df = pandas.read_csv('input.txt') # Read data from csv 
result = [] 
for column in list(df): 
    column_values = list(df[column]) 
    first_words = [x[:x.index(" ")] if " " in x else x for x in column_values] 
    result.append(func(first_words)) 

new_df = pandas.DataFrame(result).transpose() 
new_df.columns = list(df) 

print(new_df) 

出力:

 Groceries Car Luxuries 
0 Sainsbury's Texac Amazon 
1 Sainsbury's Texac Firebox 
2 Sainsbury's Shell  Sony 
3  Tesco Shell  Sony 
4  Tesco Texac Amazon 
5  Tesco Moto Amazon 

私は推測、func()機能が優れてコーディングすることができるが、これは私の心に最初に来るものです。

+0

あなたはそれが複雑だと思ってうれしいです!初心者としては、簡単な作業アイデアから始めて、それぞれのエッジケースを処理する必要があるため、複雑になることがよくあります。同時に、経験豊かなプログラマーが私のコードを大量に入れ替えてしまったことがあります。私は単純な解決策を見たことがないからです。そういうわけで私は、人々に彼らが何をしているのかを尋ねることは教育的だと思ったのです。 私はあなたの解決策を試し、あなたにお返しします。 – user4896331

関連する問題