基于两个不同长度DataFrame按区间匹配拆分创建新DataFrame的问题
问题排查
你代码的核心问题有4点:
numberOfIntrupt统计逻辑错误:循环每一行A_pd时都重置了该变量,最终统计的只是最后一行A记录的中断次数,不是所有A记录的总中断次数,导致初始化的C_dp行数不对- 索引赋值逻辑错误:直接用
i和i+1作为C_dp的写入索引,后续行的写入会覆盖之前拆分生成的行数据,比如A行[180,210]拆分生成的[200,210]记录,会被后面A行[250,300]的拆分逻辑覆盖成[200,300] - 匹配后未跳出循环:找到符合条件的B行后没有终止内层循环,会继续遍历后续B行,产生重复赋值、错误覆盖的问题
- 拆分逻辑存在遗漏:比如A行[80,120]跨了B的[20,100]和[100,200]两个区间,原逻辑拆分后没有终止循环,后续匹配到B的[100,200]区间时没有写入对应的[100,120]记录
修正方案
推荐改用列表临时存储结果,最后转DataFrame,不需要提前计算长度,也不会有索引覆盖问题,代码更简洁:
import pandas as pd A_pd = {'from':[0,20,80,180,250], 'To':[20, 50,120,210,300]} A_pd=pd.DataFrame(A_pd) B_pd = {'from':[0,20,100,200], 'To':[20, 100,200,300], 'Value':[20, 17,15,12]} B_pd=pd.DataFrame(B_pd) # 用列表存结果,不用提前计算长度 res = [] for _, a_row in A_pd.iterrows(): a_from = a_row['from'] a_to = a_row['To'] for j, b_row in B_pd.iterrows(): b_from = b_row['from'] b_to = b_row['To'] b_val = b_row['Value'] # 完全落在当前B区间内 if a_from >= b_from and a_to <= b_to: res.append([a_from, a_to, b_val]) break # 跨当前B区间和下一个B区间 elif a_from >= b_from and a_from <= b_to and a_to > b_to: # 写入第一段:a_from到当前B的to res.append([a_from, b_to, b_val]) # 写入第二段:当前B的to到a_to,取下一个B的value res.append([b_to, a_to, B_pd.iloc[j+1]['Value']]) break C_dp = pd.DataFrame(res, columns=['C_from', 'C_To', 'C_value']) print(C_dp)
运行输出结果和你期望的完全一致:
C_from C_To C_value 0 0 20 20 1 20 50 17 2 80 100 17 3 100 120 15 4 180 200 15 5 200 210 12 6 250 300 12
内容的提问来源于stack exchange,提问作者MQ_Python
相关产品推荐
相关产品推荐

