固定DF1结构,按No列将DF2数据插入对应位置的方法
如何保持DF1行顺序并将DF2数据按No值插入对应位置?
看起来你想要的不是全局按No列排序,而是保留DF1原有的行顺序,同时把DF2的行插入到DF1中相邻No值的合适位置——比如DF2中No=25的行要放在DF1里No=20和No=80的行之间,而不是把所有DF2行都堆在DF1后面。
下面是具体的实现步骤和代码:
步骤1:准备数据
先把你的两个DataFrame构造出来(如果已经有了可以跳过这步):
import pandas as pd # 构造DF1 df1 = pd.DataFrame({ 'S.NO': [1, 2, 3, 4, 5, 6], 'Let': ['A', 'B', 'C', 'D', 'F', 'G'], 'No': [10, 20, 80, 100, 8, 9] }) # 构造DF2 df2 = pd.DataFrame({ 'Name': ['Hu', 'gy', 'ga'], 'Gam1': ['Ar', 'Get', 'Gy'], 'Gam2': ['Yz', 'Tr', 'Gy'], 'No': [25, 7, 90] })
步骤2:核心实现逻辑
我们的思路是:先把DF1的行按原始顺序存起来,然后遍历DF2的每一行,找到它应该插入到DF1中的位置,最后把所有行组合成结果DataFrame。
# 把DF1的行转换成字典列表,方便逐行插入操作 df1_rows = df1.to_dict('records') # 遍历DF2的每一行,找到合适的插入位置 for _, df2_row in df2.iterrows(): target_no = df2_row['No'] insert_index = 0 # 遍历DF1的行,找到第一个No大于target_no的位置,插入到它前面 for idx, df1_row in enumerate(df1_rows): if df1_row['No'] > target_no: insert_index = idx break else: # 如果所有DF1的No都小于target_no,就插在DF1的最后 insert_index = len(df1_rows) # 把DF2的行转换成字典,补充DF1有的但DF2没有的列(设为None) row_to_insert = df2_row.to_dict() row_to_insert['S.NO'] = None row_to_insert['Let'] = None # 插入到指定位置 df1_rows.insert(insert_index, row_to_insert) # 把处理后的列表转换成DataFrame,并调整列顺序和预期一致 result_df = pd.DataFrame(df1_rows)[['S.NO', 'Let', 'No', 'Name', 'Gam1', 'Gam2']] # 打印结果(和你的预期一致) print(result_df.to_string(index=False))
运行这段代码后,输出的结果就是你想要的:
S.NO Let No Name Gam1 Gam2 1 A 10 NaN NaN NaN 2 B 20 NaN NaN NaN NaN NaN 25 Hu Ar Yz 3 C 80 NaN NaN NaN NaN NaN 90 ga Gy Gy 4 D 100 NaN NaN NaN NaN NaN 7 gy Get Tr 5 F 8 NaN NaN NaN 6 G 9 NaN NaN NaN
为什么你的sort_values方法不行?
你之前用new.sort_values(by=['No'])得到DF2全在末尾,核心原因是你误解了需求:你要的不是全局按No排序,而是保留DF1的原始行顺序,在DF1的行之间插入DF2的行。全局排序会打乱DF1原有的行顺序(比如DF1中No=8、9的行本来在最后,全局排序会跑到最前面),完全不符合你的预期;另外合并后DF2行的S.NO列是NaN,排序时这类行也容易被默认放到末尾,进一步偏离你的需求。
内容的提问来源于stack exchange,提问作者Python_newbie
相关产品推荐
相关产品推荐

