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

Pandas中跨DataFrame实现类VLOOKUP功能及InvalidIndexError解决

问题

现有两个DataFrame,需求是将df2中与df1的ID匹配的不同国家对应的URL,作为单独列合并到df1中。

df1示例数据

ID   URL
A    example.com/1
B    example.com/2
C    example.com/3
D    example.com/4

df2示例数据

ID   country    URL
A     usa       example.com/usa-A
B     uk        example.com/uk-B
C     canada    example.com/canada-C
A     uk        example.com/uk-A
C     usa       example.com/usa-C

期望合并结果

ID   URL               uk                    USA                  Canada
A    example.com/1     example.com/uk-A      example.com/usa-A    NaN
B    example.com/2     example.com/uk-B      NaN                  NaN
C    example.com/3     NaN                   example.com/usa-C    example.com/canada-C
D    example.com/4     NaN                   NaN                  NaN

尝试通过以下循环结合map实现:

final = pd.DataFrame()
for a in countries_list:
     b = df2.loc[(df2["country"] == a)]
     df1["country"] = df1['id'].map(df2.set_index('id')['url'])
     final = pd.concat([final, df1])

运行多次迭代后报错:InvalidIndexError: Reindexing only valid with uniquely valued Index objects,已尝试reset_index()仍未解决,求高效实现方式或报错解决方法。


解决方案

高效实现(推荐)

用pivot重塑df2后直接和df1合并,无需循环,代码简洁且性能更好:

import pandas as pd

# 重塑df2:将country转为列,每个ID对应各国家的URL
df2_pivot = df2.pivot(index='ID', columns='country', values='URL').reset_index()
# 左连接合并df1和重塑后的df2,保留df1所有行
result = pd.merge(df1, df2_pivot, on='ID', how='left')
# 调整列名大小写以匹配期望格式(可选)
result.columns = [col.title() if col not in ['ID', 'URL'] else col for col in result.columns]

print(result)

这段代码直接输出符合需求的结果,避免了循环带来的索引问题和冗余操作。

原代码报错修复

原报错原因是df2中存在重复的ID值(比如ID=A出现两次),用df2.set_index('id')['url']时索引不唯一,导致map操作失败。如果坚持用循环,修改如下:

import pandas as pd

# 先统一列名大小写,避免原代码中ID/id、URL/url混用的问题
df1_clean = df1.copy()
df1_clean.columns = df1_clean.columns.str.lower()
df2_clean = df2.copy()
df2_clean.columns = df2_clean.columns.str.lower()

final = df1_clean.copy()
countries_list = df2_clean['country'].unique().tolist()

for country in countries_list:
    # 筛选当前国家数据,确保ID唯一(这里取最后一条匹配记录,可根据需求改keep='first')
    country_data = df2_clean[df2_clean['country'] == country].drop_duplicates('id', keep='last')
    # 转成ID到URL的字典用于map
    url_map = country_data.set_index('id')['url'].to_dict()
    # 新增对应国家的列
    final[country.title()] = final['id'].map(url_map)

# 恢复列名大小写
final.rename(columns={'id': 'ID', 'url': 'URL'}, inplace=True)
print(final)

关键修复点:

  • 统一列名大小写,避免匹配错误
  • 对每个国家的数据去重,保证ID唯一后再生成映射字典

内容的提问来源于stack exchange,提问作者natan specialist

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.16 22:15:36