You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何修正基于关键词匹配两个Pandas DataFrame生成目标DataFrame的代码

解决Pandas DataFrame关键词匹配错误的问题

问题场景

现有两个Pandas DataFrame:df1和df2,需求是:

  • 当df2['ColD']中的完整关键词出现在df1['ColE']的文本内容中时,将df2对应行的ColA、ColB、ColC值分别合并到df1的ColA0、ColB0、ColC0列
  • 把匹配到的关键词存入ColD1列,生成目标DataFrame df01

当前代码运行后出现错误:df1第二行文本仅包含d2,却错误匹配了d1对应的A1、B1、C1,不符合预期。


错误原因分析

大概率是原有代码存在以下问题之一:

  1. 仅使用模糊的str.contains()匹配,未处理关键词边界(比如文本中的d12会被误判为包含d1)
  2. 匹配逻辑未按精确匹配顺序执行,导致无关关键词被优先匹配
  3. 使用了不合适的合并方式(如直接merge),未做逐行的精准关键词校验

正确解决方案

步骤1:构造测试示例数据

先模拟你的数据场景,方便验证:

import pandas as pd
import re

# 示例df1:待匹配的文本数据
df1 = pd.DataFrame({
    'ColE': ['文本包含d1关键词', '文本里只有d2', '同时包含d1和d3']
})

# 示例df2:关键词映射表
df2 = pd.DataFrame({
    'ColA': ['A1', 'A2', 'A3'],
    'ColB': ['B1', 'B2', 'B3'],
    'ColC': ['C1', 'C2', 'C3'],
    'ColD': ['d1', 'd2', 'd3']
})

步骤2:实现精准匹配逻辑

用apply结合正则边界校验,确保只匹配完整关键词:

# 构建关键词到对应字段的映射字典
key_map = df2.set_index('ColD')[['ColA', 'ColB', 'ColC']].to_dict('index')

# 定义匹配函数:处理单条文本的关键词匹配
def find_matches(text):
    # 收集所有匹配的完整关键词(用\b确保词边界,re.escape处理特殊字符)
    matched_keys = [
        key for key in key_map.keys()
        if re.search(rf'\b{re.escape(key)}\b', text)
    ]
    
    if not matched_keys:
        # 无匹配时返回空值
        return pd.Series([None, None, None, None])
    
    # 处理多关键词匹配:用逗号合并所有匹配结果,可按需调整(比如取第一个匹配)
    col_a_vals = ', '.join([key_map[k]['ColA'] for k in matched_keys])
    col_b_vals = ', '.join([key_map[k]['ColB'] for k in matched_keys])
    col_c_vals = ', '.join([key_map[k]['ColC'] for k in matched_keys])
    matched_str = ', '.join(matched_keys)
    
    return pd.Series([col_a_vals, col_b_vals, col_c_vals, matched_str])

# 将匹配结果合并到df1
df1[['ColA0', 'ColB0', 'ColC0', 'ColD1']] = df1['ColE'].apply(find_matches)

# 生成目标df01
df01 = df1.copy()

步骤3:验证结果

运行后df01的结果符合预期:

ColEColA0ColB0ColC0ColD1
文本包含d1关键词A1B1C1d1
文本里只有d2A2B2C2d2
同时包含d1和d3A1, A3B1, B3C1, C3d1, d3

可选调整

如果只需要第一个匹配到的关键词(而非所有匹配),可以修改find_matches函数:

def find_first_match(text):
    for key in key_map.keys():
        if re.search(rf'\b{re.escape(key)}\b', text):
            return pd.Series([key_map[key]['ColA'], key_map[key]['ColB'], key_map[key]['ColC'], key])
    return pd.Series([None, None, None, None])

内容的提问来源于stack exchange,提问作者Sanket Sathe

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.21 17:32:14