求高效Python方案:对比新旧DataFrame列并匹配添加旧数据
高效匹配新旧DataFrame并合并数据
核心优化方向
别用双重循环遍历两个数据集(这种方法时间复杂度是O(nm),10002000=200万次操作,既慢又容易出问题),改用批量模糊匹配工具结合pandas的向量化操作,既高效又能避免索引越界。
推荐实现方案(基于RapidFuzz,速度拉满)
步骤1:安装依赖
pip install rapidfuzz pandas
步骤2:代码实现
假设你要匹配的列叫match_col,需要从旧DataFrame提取的信息列叫need_info_col:
import pandas as pd from rapidfuzz import process, fuzz # 导入数据 new_df = pd.read_csv("你的新数据文件路径") old_df = pd.read_csv("你的旧数据文件路径") # 把旧表的匹配列和目标列转成列表,方便快速匹配 old_match_values = old_df["match_col"].tolist() old_info_values = old_df["need_info_col"].tolist() # 定义匹配函数:输入新表的一个值,返回符合相似度要求的旧表信息 def get_matched_info(val, similarity_threshold=80): # 找旧表中相似度最高的结果(scorer用fuzz.ratio计算文本相似度,满分100) best_match = process.extractOne(val, old_match_values, scorer=fuzz.ratio) if best_match and best_match[1] >= similarity_threshold: # best_match[2]是旧表中匹配项的索引,直接取对应信息 return old_info_values[best_match[2]] # 不满足阈值就返回空 return None # 把匹配结果批量加到新表中(pandas的apply是向量化操作,比手动循环稳) new_df["matched_old_info"] = new_df["match_col"].apply(get_matched_info)
解决你之前的两个问题
- 未遍历完整数据集:这个方法会处理新表的每一条数据,并且对每条数据在旧表中做全局匹配,不会漏掉任何一条
- 索引越界:
process.extractOne返回的索引是旧表的有效索引,结合预存的列表取值,不会出现超出DataFrame长度的情况;同时用pandas的apply自动处理行索引,不用手动操作索引,从根源避免越界问题
额外优化建议
如果你的匹配列是数值型,可以不用模糊匹配,直接用pd.merge_asof(按数值接近度合并),速度更快:
# 先对两个DataFrame按数值列排序 new_df_sorted = new_df.sort_values("numeric_match_col") old_df_sorted = old_df.sort_values("numeric_match_col") # 按数值接近度合并,设置容差(比如允许数值差在5以内) merged_df = pd.merge_asof(new_df_sorted, old_df_sorted, on="numeric_match_col", tolerance=5, direction="nearest")
内容的提问来源于stack exchange,提问作者Combine8820
相关产品推荐
相关产品推荐

