如何从df_1匹配id_1/id_2,将对应value值填入df_2?
Pandas根据ID匹配提取指定字段值填充DataFrame
原始DataFrame定义
df_1的定义与数据
import pandas as pd df_1 = pd.DataFrame( { "id_1": [1, 1, 2, 2], "id_2": [11, 11, 22, 22], "value_1": [0.1, 0.1, 0.01, 0.01], "value_2": [0.2, 0.2, 0.02, 0.02], "value_3": [0.3, 0.3, 0.03, 0.03], } )
数据展示:
id_1 id_2 value_1 value_2 value_3 0 1 11 0.10 0.20 0.30 1 1 11 0.10 0.20 0.30 2 2 22 0.01 0.02 0.03 3 2 22 0.01 0.02 0.03
df_2的定义与数据
df_2 = pd.DataFrame( { "id_1": [1, 1, 1, 1, 2, 2, 2, 2], "id_2": [11, 11, 11, 11, 22, 22, 22, 22], "value_name": [ "value_1", "value_2", "value_3", "value_1", "value_1", "value_2", "value_3", "value_1", ], } )
数据展示:
id_1 id_2 value_name 0 1 11 value_1 1 1 11 value_2 2 1 11 value_3 3 1 11 value_1 4 2 22 value_1 5 2 22 value_2 6 2 22 value_3 7 2 22 value_1
需求
根据id_1和id_2的匹配关系,从df_1中获取value_name列指定的value值,填充到df_2中,最终得到包含value列的目标DataFrame。
解决方案
方法一:宽表转长表后合并
先对df_1去重(同一id_1+id_2组合的value值完全重复),再将df_1从宽格式转换为长格式,最后与df_2合并:
# 去重,保留每个id组合的唯一值 df_1_unique = df_1.drop_duplicates(subset=['id_1', 'id_2']) # 转长表,将value_1/2/3列转为value_name和value的键值对 df_1_melted = df_1_unique.melt( id_vars=['id_1', 'id_2'], var_name='value_name', value_name='value' ) # 合并df_2和转换后的df_1,得到结果 result = pd.merge(df_2, df_1_melted, on=['id_1', 'id_2', 'value_name'], how='left')
方法二:合并后按列名提取值
先合并df_2与去重后的df_1,再通过value_name列的值动态提取对应列的value:
# 去重df_1并与df_2合并 merged_df = pd.merge(df_2, df_1.drop_duplicates(subset=['id_1', 'id_2']), on=['id_1', 'id_2'], how='left') # 根据value_name提取对应列的数值 merged_df['value'] = merged_df.apply(lambda row: row[row['value_name']], axis=1) # 保留需要的列 result = merged_df[['id_1', 'id_2', 'value_name', 'value']]
两种方法均可得到目标结果,方法一性能更优(尤其数据量较大时),避免了逐行apply的开销。
内容的提问来源于stack exchange,提问作者ajrlewis
相关产品推荐
相关产品推荐

