Python 熊猫在同一列中用模糊匹配替换字符串
我在数据帧中有一列,如下所示:Python 熊猫在同一列中用模糊匹配替换字符串,python,regex,pandas,fuzzy-comparison,difflib,Python,Regex,Pandas,Fuzzy Comparison,Difflib,我在数据帧中有一列,如下所示: OWNER -------------- OTTO J MAYER OTTO MAYER DANIEL J ROSEN DANIEL ROSSY LISA CULLI LISA CULLY LISA CULLY CITY OF BELMONT CITY OF BELMONT CITY 我的数据框中的一些名称拼写错误,或者有多余/缺少的字符。我需要一个列,其中的名称替换为同一列中的任何密切匹配项。但是,所有相似的名称都需要在同一个名称下分
OWNER
--------------
OTTO J MAYER
OTTO MAYER
DANIEL J ROSEN
DANIEL ROSSY
LISA CULLI
LISA CULLY
LISA CULLY
CITY OF BELMONT
CITY OF BELMONT CITY
我的数据框中的一些名称拼写错误,或者有多余/缺少的字符。我需要一个列,其中的名称替换为同一列中的任何密切匹配项。但是,所有相似的名称都需要在同一个名称下分组
例如,这就是我从上面的数据框中所期望的:
NAME
--------------
OTTO J MAYER
OTTO J MAYER
DANIEL J ROSEN
DANIEL ROSSY
LISA CULLY
LISA CULLY
LISA CULLY
CITY OF BELMONT
CITY OF BELMONT
OTTO MAYER被OTTO J MAYER取代,因为两者非常相似。但以理一家还是老样子,因为他们不太般配。LISA CULL都有相同的值等等
我从另一篇关于堆栈溢出的文章中得到了一些代码,这篇文章试图解决类似的问题,但它们使用的是名称词典。然而,我在修改他们的代码以产生所需的输出时遇到了困难
以下是我目前的情况:
d = pd.DataFrame({'OWNER' : pd.Series(['OTTO J MAYER', 'OTTO MAYER','DANIEL J ROSEN','DANIEL ROSSY',
'LISA CULLI', 'LISA CULLY'])})
names = d['OWNER']
names = names.values
names
import difflib
def best_match(tokens, names):
for i,t in enumerate(tokens):
closest = difflib.get_close_matches(t, names, n=1)
if len(closest) > 0:
return i, closest[0]
return None
def fuzzy_replace(x, y):
names = y # just a simple replacement list
tokens = x.split()
res = best_match(tokens, y)
if res is not None:
pos, replacement = res
return u" ".join(tokens)
return x
d["OWNER"].apply(lambda x: fuzzy_replace(x, names))
的确,它适合于此任务,但将名称拆分为标记并没有什么好处。为了区分指定的名称,我们必须将截止分数提高到0.8左右,并确保返回所有可能的名称,将最大值提高到len(names)
。然后我们有两个案例来决定选择哪个名称:
- 如果一个名字出现的次数比其他名字多,请选择该名字
- 否则,选择首先出现的一个
def fuzzy_replace(x, names):
aliases = difflib.get_close_matches(x, names, len(names), .8)
closest = pd.Series(aliases).mode()
closest = aliases[0] if closest.empty else closest[0]
d['OWNER'].replace(aliases, closest, True)
for x in d["OWNER"]: fuzzy_replace(x, d['OWNER'])