Pandas如何仅在匹配字典键时映射,避免覆盖已有值?
解决DataFrame映射时避免覆盖已有值的问题
场景1:按优先级填充空值
如果希望按「ALIAS_NAME → ASSET_NAME → SERIAL」的优先级尝试匹配,仅当当前id为空时,用下一个字段的匹配值填充,可以使用fillna方法:
# 初始化为ALIAS_NAME的映射结果 df["id"] = df["ALIAS_NAME"].str.lower().map(all_hostnames) # 用ASSET_NAME的匹配值填充id列空值 df["id"] = df["id"].fillna(df["ASSET_NAME"].str.lower().map(all_hostnames)) # 用SERIAL的匹配值填充剩余空值 df["id"] = df["id"].fillna(df["SERIAL"].map(all_serials))
若需要将SERIAL设为最高优先级(优先用序列号匹配),调整顺序即可:
df["id"] = df["SERIAL"].map(all_serials) df["id"] = df["id"].fillna(df["ASSET_NAME"].str.lower().map(all_hostnames)) df["id"] = df["id"].fillna(df["ALIAS_NAME"].str.lower().map(all_hostnames))
场景2:高优先级匹配覆盖已有值
如果希望高优先级字段的匹配结果覆盖低优先级(比如ASSET_NAME匹配结果替换ALIAS_NAME的,SERIAL匹配结果替换前两者),但仅当字段能匹配到字典时才修改(不会把已有有效值改为NaN),可以结合loc和非空判断实现:
# 初始化为ALIAS_NAME的映射结果 df["id"] = df["ALIAS_NAME"].str.lower().map(all_hostnames) # 仅更新ASSET_NAME能匹配到的行 asset_map = df["ASSET_NAME"].str.lower().map(all_hostnames) df.loc[asset_map.notna(), "id"] = asset_map.dropna() # 仅更新SERIAL能匹配到的行 serial_map = df["SERIAL"].map(all_serials) df.loc[serial_map.notna(), "id"] = serial_map.dropna()
内容的提问来源于stack exchange,提问作者Empusas
相关产品推荐
相关产品推荐

