Python 什么';合并前清理数据的更好方法是什么?
我有两个不同的数据帧需要合并,合并列(“标题”)需要在合并之前清除。示例数据示例如下所示Python 什么';合并前清理数据的更好方法是什么?,python,pandas,replace,merge,Python,Pandas,Replace,Merge,我有两个不同的数据帧需要合并,合并列(“标题”)需要在合并之前清除。示例数据示例如下所示 data1 = pd.DataFrame({'id': ['a12bcde0','b20bcde9'], 'title': ['a.b. company','company_b']}) data2 = pd.DataFrame({'serial_number': ['01a2b345','10ab2030','40ab4060'],'title':['ab company','company_b (123
data1 = pd.DataFrame({'id': ['a12bcde0','b20bcde9'], 'title': ['a.b. company','company_b']})
data2 = pd.DataFrame({'serial_number': ['01a2b345','10ab2030','40ab4060'],'title':['ab company','company_b (123)','company_f']})
正如预期的那样,合并不会在第一个标题上成功。我一直在使用replace()
方法,但由于拼写、区分大小写等原因,我有100多个标题需要更正,因此它很快变得难以管理
关于如何最好地清理和合并数据,还有其他建议吗
完整示例:
import pandas as pd
import numpy as np
data1 = pd.DataFrame({'id': ['a12bcde0','b20bcde9'], 'title': ['a.b. company','company_b']})
data2 = pd.DataFrame({'serial_number': ['01a2b345','10ab2030','40ab4060'],'title':['ab company','company_b (123)','company_f']})
data2['title'].replace(regex=True,inplace=True,to_replace=r"\s\(.*\)",value=r'')
replacements = {
'title': {
r'a.b. company *.*': 'ab company'
}
}
data1.replace(replacements, regex=True, inplace=True)
pd.merge(data1, data2, on='title')
您可以尝试在两个数据帧中的每一个数据帧中创建一个简化的_name列,方法是将所有字符设置为小写,并删除所有非[a-z]字符,然后在此列上进行连接,如果这不会导致冲突的话。首先,这个问题没有完美的解决方案,但我建议做两件事:
- 做任何简单的清洁,你可以做的手,包括删除任何字符你不期望
- 应用模糊匹配逻辑
首先,让我们先让您的示例稍微复杂一点,引入一个常规的打字错误(
coampany\u b
,而不是company\u b
,这是通过下面的简单清理不会发现的)
那么让我们假设您只需要@Maarten Fabré提到的[a-z]角色。因此,让我们将所有内容小写,并删除所有其他内容
data1['cleaned_title'] = data1['title'].str.lower().replace(regex=True,inplace=False,to_replace=r"[^a-z]", value=r'')
data2['cleaned_title'] = data2['title'].str.lower().replace(regex=True,inplace=False,to_replace=r"[^a-z]", value=r'')
现在,让我们使用(阅读更多和其他选项) 这是结果数据1,看起来不错
id title cleaned_title closestmatch
0 a12bcde0 a.b. company abcompany abcompany
1 b20bcde9 company_b companyb companyb
2 csdfsjkbku coampany_b coampanyb companyb
现在,这里是数据2,看起来有点不太好。。。我们要求它找到最接近的匹配项,因此它为f公司找到了一个匹配项,而您显然不想要它
serial_number title cleaned_title closestmatch
0 01a2b345 ab company abcompany abcompany
1 10ab2030 company_b (123) companyb companyb
2 40ab4060 company_f companyf companyb
理想的情况是,如果你有一个清晰的公司名称列表,在这种情况下,你应该在此基础上找到最接近的匹配项。如果你不这样做,你将不得不发挥创意或手动清理命中和未命中
总而言之,您现在可以在“ClosesMatch”上执行常规合并。我想不出比这更好的方法了。。。你在想什么?你可以使用这个包,比如使用函数
ratio
。
id title cleaned_title closestmatch
0 a12bcde0 a.b. company abcompany abcompany
1 b20bcde9 company_b companyb companyb
2 csdfsjkbku coampany_b coampanyb companyb
serial_number title cleaned_title closestmatch
0 01a2b345 ab company abcompany abcompany
1 10ab2030 company_b (123) companyb companyb
2 40ab4060 company_f companyf companyb