如何更高效地按ID分组配对合并DataFrame的SEQ列元素?
如何更高效地按ID分组配对合并DataFrame的SEQ列元素?
嘿,你的实现思路完全没问题,但确实能简化得更高效,不用生成那么多中间列,处理逻辑也能更聚焦核心需求——咱们直接围绕「同ID分组内,将当前行SEQ与下一行SEQ合并」这个目标来优化:
先回顾下你的原始数据:
import pandas as pd x = pd.DataFrame({ 'ID': [1, 1, 1, 1, 2, 2, 2], 'SEQ': [1, 2, 3, 4, 1, 3, 4] })
对应的输出效果是要得到同ID内相邻SEQ的配对,比如1 - 2、2 - 3这类组合。
优化方案1:分组Shift+直接过滤(高效简洁)
核心是用groupby在同ID分组内做shift(-1),这样跨ID的行不会被错误匹配,而且自动在每组最后一行生成NaN,直接过滤掉这些空值就行,不用额外对比ID:
# 先把SEQ转成字符串,方便拼接 x['SEQ'] = x['SEQ'].astype(str) # 仅在同ID分组内,获取下一行的SEQ值并拼接 x['COMBINE'] = x['SEQ'] + ' - ' + x.groupby('ID')['SEQ'].shift(-1) # 过滤掉没有下一行的行(每组最后一行的COMBINE会是NaN) x = x.dropna(subset=['COMBINE']) # 保留需要的列(可选,根据你的需求调整) x = x[['ID', 'SEQ', 'COMBINE']]
运行后得到的结果和你预期的完全一致:
ID SEQ COMBINE 0 1 1 1 - 2 1 1 2 2 - 3 2 1 3 3 - 4 4 2 1 1 - 3 5 2 3 3 - 4
优化方案2:链式操作(更紧凑的写法)
如果喜欢代码更紧凑,用pandas的链式调用可以把所有逻辑串起来,不用分步赋值:
x = (pd.DataFrame({ 'ID': [1, 1, 1, 1, 2, 2, 2], 'SEQ': [1, 2, 3, 4, 1, 3, 4] }) .assign(SEQ=lambda df: df['SEQ'].astype(str)) .assign(COMBINE=lambda df: df['SEQ'] + ' - ' + df.groupby('ID')['SEQ'].shift(-1)) .dropna(subset=['COMBINE']) .filter(items=['ID', 'SEQ', 'COMBINE']))
为什么这些方法更高效?
- 减少冗余列:不需要生成
ID_NEXT这类中间列,直接聚焦核心的SEQ配对逻辑,节省内存; - 分组操作更精准:
groupby('ID').shift(-1)只会在同ID内部做下移,不会处理跨ID的行,避免了全表shift后再过滤的冗余计算,大数据量下性能提升更明显; - 逻辑更清晰:代码直接对应需求——“同ID内,当前SEQ拼接下一行SEQ”,读起来一目了然。
备注:内容来源于stack exchange,提问作者obchardon
相关产品推荐
相关产品推荐

