我想按类型和国家对数据框进行分组,并删除那些较长的电话号码Prefix
,如果有较短的前缀相同的类型和国家。
例如基于以下输入:
前缀 | 类型 | 国家 |
---|---|---|
43 | 修复线 | 奥地利 |
431 | 修复线 | 奥地利 |
43650 | 移动 | 奥地利 |
436501 | 移动 | 奥地利 |
43676 | 移动 | 奥地利 |
我想要以下输出。
前缀 | 类型 | 国家 |
---|---|---|
43 | 修复线 | 奥地利 |
43650 | 移动 | 奥地利 |
43676 | 移动 | 奥地利 |
431 被删除,因为已经存在与 431 和 431 相同类型和国家/地区的前缀 43 > 以 43 开头。
436501 被删除,因为已经存在与 436501 和 436501 相同类型和国家/地区的前缀 43650 > 以 43650 开头。
我对 Pandas 没有太多经验。 我的第一次尝试是这个,但这需要太长时间:
for index, row in data.iterrows():
for index2, row2 in data.iterrows():
if index2 > index and row['Type'] == row2['Type'] and row['Country'] == row2['Country'] and row['Prefix'].startswith(row2['Prefix']):
data.drop(index, inplace=True)
break
答案 0 :(得分:1)
我认为最明智的做法是先将 Prefix
切片为想要的并知道长度,然后删除重复项。
df = pd.DataFrame({'Prefix':[43, 431, 43650, 436501, 43676],
'Type':['Fixline', 'Fixline', 'Mobile', 'Mobile', 'Mobile'],
'Country':['Austria']*5})
df['Prefix'] = df[['Prefix', 'Type']].apply(lambda x: str(x[0])[:2] if x[1]=='Fixline' else str(x[0])[:5], axis=1)
df = df.drop_duplicates()
df
>>>
Prefix Type Country
0 43 Fixline Austria
2 43650 Mobile Austria
4 43676 Mobile Austria
答案 1 :(得分:1)
您的 DataFrame 中的 Prefix 列可能是 int 类型, 所以第一件事就是把它转换成String:
df.Prefix = df.Prefix.astype(str)
然后定义2个函数:
检查当前行是否存在的函数 Prefix 较短的另一行,这也是“起始部分” “我的”前缀:
def hasShorter(row, grp):
myPref = row.Prefix
ind = row.name
prefsToCompare = grp.drop(ind).Prefix
# Leave only shorter Prefixes
prefsToCompare = prefsToCompare[prefsToCompare.str.len() < len(myPref)]
if prefsToCompare.size == 0:
return False # No rows with shorter prefix
# Is any other Prefix less specific?
return prefsToCompare.apply(lambda x: myPref.startswith(x)).any()
应用于每个组的函数 - 过滤器,消除行 没有任何更短的“邻居前缀”(以相同的开头 字符):
def groupFilter(grp):
return grp[~grp.apply(hasShorter, axis=1, grp=grp)]
然后,要获得预期的结果,请运行:
result = df.groupby(['Type', 'Country'], as_index=False,
group_keys=False).apply(groupFilter)
对于您的数据样本,结果是:
Prefix Type Country
0 43 Fixline Austria
2 43650 Mobile Austria
4 43676 Mobile Austria
如果需要,将 Prefix 列转换回 int。 或者,该列最初是并且应该保持为 str 类型 (你的前缀只是代码,不小心只由数字组成, 但应该被视为字符串)?