pandas按O-D分组合并后如何用df.loc筛选对应PersonID
Pandas按OD对分组后过滤原始记录空结果问题解决
错误原因
- 多级列索引问题:你对
PersonID字段同时聚合了count和list两个指标,生成的dfm、merged都是多级列索引,直接调用merged['PersonID']得到的是包含count、list两个子列的DataFrame,不是你要的ID值 - 值格式不匹配:
merged里存PersonID的是('PersonID', 'list')列,每一行都是列表类型,你直接把列表对象放进isin匹配单个字符串类型的PersonID,自然匹配不到任何结果,返回空表 - 小笔误:你代码里定义出租车表时变量名写的是
tax,后续分组用了taxi,会触发变量未定义报错,先统一变量名即可
解决方法
方法1:基于已生成的merged表提取目标ID
把merged里所有PersonID列表打平为一维集合,再用集合过滤原始df:
import pandas as pd df = pd.DataFrame({'PersonID':['1','1','2','2','2','3'],'O':['A','B','C','B','A','X'],'D':['B','A','B','A','B','Y']}) # 修正变量名笔误 taxi = pd.DataFrame({'TaxiID':['T1','T2','T3'],'O':['B','A','C'],'D':['A','B','B']}) df_grouped = df.groupby(['O','D']) tax_grouped = taxi.groupby(['O','D']) dfm = df_grouped.agg({'PersonID':['count',list]}).reset_index() tgm = tax_grouped.agg({'TaxiID':['count',list]}).reset_index() merged = pd.merge(dfm, tgm, how='inner') # 打平所有PersonID列表,得到目标ID集合 target_pids = set() for pid_list in merged[('PersonID', 'list')]: target_pids.update(pid_list) # 过滤原始df seek = df[df['PersonID'].isin(target_pids)]
执行后seek会返回PersonID为1、2的所有记录,符合预期。
方法2:更简洁的OD对直接过滤(无需聚合list)
因为merged是OD对的内连接结果,本质上你要的是OD对同时出现在两个表中的原始记录,可以不用存PersonID列表,直接匹配OD对即可:
# 先拿到两个表共有的OD对集合 valid_ods = set(zip(taxi['O'], taxi['D'])) # 直接过滤df中OD对符合要求的记录 seek = df[df[['O','D']].apply(tuple, axis=1).isin(valid_ods)]
这个方法逻辑更清晰,性能也更好。
内容的提问来源于stack exchange,提问作者Ricky
相关产品推荐
相关产品推荐

