Python 不同数据帧的模糊匹配列

Python 不同数据帧的模糊匹配列,python,pandas,fuzzy-logic,fuzzy-comparison,fuzzywuzzy,Python,Pandas,Fuzzy Logic,Fuzzy Comparison,Fuzzywuzzy,背景 我有两个数据帧,没有公共密钥,我可以将它们合并到其中。两个df都有一个包含“实体名称”的列。一个df包含8000多个实体,另一个接近2000个实体 样本数据: vendor_df= Name of Vendor City State ZIP FREDDIE LEES AMERICAN GOURMET SAUCE St. Louis MO 63101 CITYAR

背景

我有两个数据帧,没有公共密钥,我可以将它们合并到其中。两个df都有一个包含“实体名称”的列。一个df包含8000多个实体,另一个接近2000个实体

样本数据

vendor_df=
     Name of Vendor                             City         State  ZIP
     FREDDIE LEES AMERICAN GOURMET SAUCE       St. Louis    MO     63101
     CITYARCHRIVER 2015 FOUNDATION             St. Louis    MO     63102
     GLAXOSMITHKLINE CONSUMER HEALTHCARE       St. Louis    MO     63102
     LACKEY SHEET METAL                        St. Louis    MO     63102

regulator_df = 
     Name of Entity                    Committies
     LACKEY SHEET METAL                 Private
     PRIMUS STERILIZER COMPANY LLC      Private  
     HELGET GAS PRODUCTS INC            Autonomous
     ORTHOQUEST LLC                     Governmant  
问题Stmt:

我必须模糊匹配这两个(
Name of vendor
&
Name of Entity
)列的实体,并获得分数。因此,需要知道dataframe 1的第一个值(
vendor_df
)是否与dataframe 2的2000个实体中的任何一个匹配(regulator_df

我检查的堆栈溢出链接

vendor_df=
     Name of Vendor                             City         State  ZIP
     FREDDIE LEES AMERICAN GOURMET SAUCE       St. Louis    MO     63101
     CITYARCHRIVER 2015 FOUNDATION             St. Louis    MO     63102
     GLAXOSMITHKLINE CONSUMER HEALTHCARE       St. Louis    MO     63102
     LACKEY SHEET METAL                        St. Louis    MO     63102

regulator_df = 
     Name of Entity                    Committies
     LACKEY SHEET METAL                 Private
     PRIMUS STERILIZER COMPANY LLC      Private  
     HELGET GAS PRODUCTS INC            Autonomous
     ORTHOQUEST LLC                     Governmant  

代码

import pandas as pd
from fuzzywuzzy import fuzz
from fuzzywuzzy import process

vendor_df = pd.read_excel('C:\\Users\\40101584\\Desktop\\AUS CUB AML\\Vendors_Sheet.xlsx', sheet_name=0)

regulator_df = pd.read_excel('C:\\Users\\40101584\\Desktop\\AUS CUB AML\\Regulated_Vendors_Sheet.xlsx', sheet_name=0)

compare = pd.MultiIndex.from_product([vendor_df['Name of vendor'],
                                      regulator_df['Name of Entity']]).to_series()


def metrics(tup):
    return pd.Series([fuzz.ratio(*tup),
                      fuzz.token_sort_ratio(*tup)],
                     ['ratio', 'token'])

#compare.apply(metrics) -- Either this works or the below line

result = compare.apply(metrics).unstack().idxmax().unstack(0)
上述代码存在问题

vendor_df=
     Name of Vendor                             City         State  ZIP
     FREDDIE LEES AMERICAN GOURMET SAUCE       St. Louis    MO     63101
     CITYARCHRIVER 2015 FOUNDATION             St. Louis    MO     63102
     GLAXOSMITHKLINE CONSUMER HEALTHCARE       St. Louis    MO     63102
     LACKEY SHEET METAL                        St. Louis    MO     63102

regulator_df = 
     Name of Entity                    Committies
     LACKEY SHEET METAL                 Private
     PRIMUS STERILIZER COMPANY LLC      Private  
     HELGET GAS PRODUCTS INC            Autonomous
     ORTHOQUEST LLC                     Governmant  
如果两个数据帧都很小,那么代码就可以工作,但是当我给出完整的数据集时,它会花费很长时间。以上代码取自第三链接

如果相同的东西可以快速工作或可以处理大型数据集,有什么解决方案吗?

更新1


如果我们通过或硬编码一个分数,比如说80,它将只使用fuzzyscore>80过滤系列/数据帧,那么上述代码是否可以更快?

下面的解决方案比我发布的要快,但如果有人有更快的方法,请告知:

matched_vendors = []

for row in vendor_df.index:
    vendor_name = vendor_df.get_value(row,"Name of vendor")
    for columns in regulator_df.index:
        regulated_vendor_name=regulator_df.get_value(columns,"Name of Entity")
        matched_token=fuzz.partial_ratio(vendor_name,regulated_vendor_name)
        if matched_token> 80:
            matched_vendors.append([vendor_name,regulated_vendor_name,matched_token])

在我的情况下,我也需要寻找只有80以上。我根据我的用例修改了你的代码。希望对你有所帮助

compare = compare.apply(metrics)
compare_80=compare[(compare['ratio'] >80) & (compare['token'] >80)]

我遇到了同样的问题,但这里您运行了两次
compare.apply(metrics)
,应用比率和令牌需要很长时间,也许你最好评论最后一行事实上我已经尝试了这两种方法…这两种方法对我来说都花了很长时间。你应该尝试使用多进程或线程。Aarwal我得到AttributeError:“collections.OrderedDict”对象没有属性“index”。。。我需要把你的dict值转换成列表谢谢。因此,我的工作持续了24小时。。这是我的2Q任何帮助PLZ在你的问题上贴了一个链接…检查一下…我实现了它,效果很好!!