保留重复索引的Pandas DataFrame新增列问题
问题分析与解决方案
错误原因
你遇到的9行笛卡尔积问题,是因为两个DataFrame的BS索引存在重复值(均为3个999)。join操作会基于索引值进行全匹配,导致每个999行互相配对,最终产生3×3=9行的结果。
正确实现方法
方法一:直接列赋值(适用于行数一致、行顺序对应场景)
当两个DataFrame的行数完全相同,且行顺序一一对应时,直接将新列赋值到原DataFrame即可:
import pandas as pd # 初始化原DataFrame value = {'M1': [3.65, 3.58, 3.5], 'BS': [999, 999, 999], 'RAW':['A', 'B', 'C']} df = pd.DataFrame(value).set_index('BS') # 初始化含M2列的DataFrame value = {'M2': [3.35, 3.38, 3.3], 'BS': [999, 999, 999]} df1 = pd.DataFrame(value).set_index('BS') # 按行位置直接赋值M2列 df['M2'] = df1['M2'].values
方法二:按列合并(适用于行数一致场景)
使用pd.concat按列合并两个DataFrame,自动按行位置对齐,避免索引匹配导致的笛卡尔积:
import pandas as pd value = {'M1': [3.65, 3.58, 3.5], 'BS': [999, 999, 999], 'RAW':['A', 'B', 'C']} df = pd.DataFrame(value).set_index('BS') value = {'M2': [3.35, 3.38, 3.3], 'BS': [999, 999, 999]} df1 = pd.DataFrame(value).set_index('BS') # 按列合并 df = pd.concat([df, df1], axis=1)
方法三:处理缺失索引场景
如果需要兼容新DataFrame存在缺失/额外BS索引的情况,可以通过添加辅助行号列来保证行对应关系:
import pandas as pd # 原DataFrame添加行号辅助列 value = {'M1': [3.65, 3.58, 3.5], 'BS': [999, 999, 999], 'RAW':['A', 'B', 'C']} df = pd.DataFrame(value).assign(row_id=range(len(value['M1']))).set_index('BS') # 含M2列的DataFrame添加行号辅助列(模拟存在额外BS的情况) value = {'M2': [3.35, 3.38, 3.3, 3.25], 'BS': [999, 999, 999, 888]} df1 = pd.DataFrame(value).assign(row_id=range(len(value['M2']))).set_index('BS') # 基于BS和row_id合并,避免笛卡尔积 df = df.reset_index().merge(df1.reset_index(), on=['BS', 'row_id'], how='outer').set_index('BS') # 删除辅助列 df = df.drop('row_id', axis=1)
内容的提问来源于stack exchange,提问作者Roberto Fichera
相关产品推荐
相关产品推荐

