Pandas如何基于Description字段条件修改对应行Cat_Tier_2列值
原代码失效原因
- 原生
if/elif是单值判断逻辑,直接传pandas的Series列对象时,"xxx" in df["列名"]只会判断关键词是否存在于列的索引中,不会逐行扫描文本内容 str.replace方法只会返回替换后的新Series,不把结果赋值回原列的话,不会对原表数据产生任何修改- 你的需求是满足行条件时整格替换为固定值,不需要用字符串替换方法,直接按条件赋值即可
推荐实现方案
优先用向量化操作,性能远高于逐行循环,数据量大的时候差距非常明显。
方法1:loc布尔索引赋值(最直观,适合分支少的场景)
先把Description列统一转小写,避免大小写不一致导致匹配遗漏,加na=False跳过空值防止报错:
desc_lower = df["Description"].str.lower() # 匹配到wireless的行,Cat_Tier_2赋值为Wireless df.loc[desc_lower.str.contains("wireless", na=False), "Cat_Tier_2"] = "Wireless" # 匹配到corded的行,Cat_Tier_2赋值为Corded df.loc[desc_lower.str.contains("corded", na=False), "Cat_Tier_2"] = "Corded"
如果两个关键词可能同时出现在同一条Description里,上面的写法会以后面的赋值规则为准,你可以根据业务优先级调整两行代码的顺序。
方法2:np.select 多条件匹配(适合分支多的场景,可读性更好)
把所有判断条件和对应目标值按顺序列出来即可,未命中任何条件的行可以通过default参数保留原值:
import numpy as np desc_lower = df["Description"].str.lower() conditions = [ desc_lower.str.contains("wireless", na=False), desc_lower.str.contains("corded", na=False) ] target_values = ["Wireless", "Corded"] df["Cat_Tier_2"] = np.select(conditions, target_values, default=df["Cat_Tier_2"])
方法3:逐行apply自定义函数(和原生if逻辑写法最接近,仅适合小数据量)
如果习惯写原生if判断,可以用apply逐行传入判断逻辑,本质是Python层循环,数据量超过10万行时运行速度会明显变慢:
def match_category(row): desc_text = str(row["Description"]).lower() if "wireless" in desc_text: return "Wireless" elif "corded" in desc_text: return "Corded" # 不满足条件保留原值 return row["Cat_Tier_2"] # axis=1表示按行传入数据 df["Cat_Tier_2"] = df.apply(match_category, axis=1)
注意:所有pandas修改列值的操作,都需要把运算/筛选后的结果重新赋值回对应列,或者用
loc直接定位位置赋值,单独调用方法不接收返回值不会修改原数据。
内容的提问来源于stack exchange,提问作者Shaggy89
相关产品推荐
相关产品推荐

