如何通过Class列表匹配split列值,填充DataFrame的Category列NaN值?
问题需求
判断DataFrame的split列内容是否包含Class列表中的元素,若匹配成功则使用匹配到的Class列表值更新Category列的空值,最终得到示例中Desired Category列的预期结果。
示例数据
domain split Category Desired Category abc@XYT.com XYT.com Null XYT abb@XTY.com XTY.com Null Null abc@ssa.com ssa.com Null ssa bbb@bbc.com bbc.com Null bbc ccc@abk.com abk.com Null abk acc@ssb.com ssb.com Null ssb
匹配用的参考列表:
Class=['NaN','XYT','ssa','abk','abc','def','asds','ssb','bbc','XY','ab']
原代码问题排查
你编写的原代码如下:
for index, row in df.iterrows(): for x in class: intersection=row.split.contains(x) if intersection: df.loc[index,'class'] = intersection
存在以下几处错误:
class是Python保留关键字,不能直接作为变量名使用,运行会直接报语法错误- 取行字段的写法错误:
row.split会被识别为调用字符串的split切分方法,而不是取列名为split的字段值,应该写为row['split'] - 包含判断逻辑错误:
contains是Pandas Series的矢量化字符串方法,单条字符串判断是否包含子串应该用Python原生的in关键字 - 赋值逻辑错误:你把布尔类型的匹配结果赋值给了不存在的
class列,而非目标Category列,且应该赋值匹配到的x值而非布尔值 - 未处理匹配优先级问题:如果
split值同时匹配多个Class元素(比如XYT.com同时匹配XY和XYT),短字符串会先命中导致结果不符合预期,需要先把Class列表按字符串长度降序排序,优先匹配更长的元素 - 未过滤无效匹配项:
Class列表里的'NaN'字符串无实际匹配意义,会导致空值被误匹配,需要提前移除
正确实现代码
import pandas as pd import numpy as np # 预处理匹配列表:移除NaN字符串,按长度降序排序,优先匹配长字符串 match_list = [x for x in Class if x != 'NaN'] match_list_sorted = sorted(match_list, key=lambda x: len(x), reverse=True) # 遍历更新Category列 for index, row in df.iterrows(): # 仅处理Category列为空的行 if pd.isna(row['Category']): split_val = row['split'] match_res = np.nan for x in match_list_sorted: if x in split_val: match_res = x break # 匹配到最长的就退出,避免短字符串覆盖 df.loc[index, 'Category'] = match_res
运行上述代码后Category列就会和示例中的Desired Category结果一致。
内容的提问来源于stack exchange,提问作者one_random_python_learner
相关产品推荐
相关产品推荐

