You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

按分组统计DataFrame两列中值的首次与二次出现情况

问题描述

现有一个已按Ref1和Seq排序的DataFrame,结构如下:

Ref1EvnNoP1P2SeqPP1PP2
aaaa0xxxyyy101
aaaa0xxxyyy200
aaaa0xxxyyy310
aaaa0xxxyyy400
aaaa1xxxyyy500
aaaa1xxxyyy610
aaaa1xxxyyy710
aaaa1xxxyyy801
bbbb0xxxyyy100
bbbb0xxxyyy200
bbbb0xxxyyy300
bbbb0xxxyyy400
bbbb1xxxyyy500
bbbb1xxxyyy600
bbbb1xxxyyy710
bbbb1xxxyyy801

需要完成两项统计任务:

  • 按Ref1和EvNo分组,统计PP1或PP2列中首次出现1的次数(分组内可能无1出现,同一行的PP1和PP2不会同时为1)。
  • 若分组内存在1的首次出现,统计首次出现后另一列出现1的情况:比如首次出现的1在PP1列,则只统计后续PP2列的1;若后续1仍在PP1列则不计入,分组内可能无后续1出现。

预期输出:

P1 First OccP2 First OccP1 Second OccP2 Second Occ
2101
解决方案

可以用Pandas的分组操作结合自定义函数实现需求,代码如下:

import pandas as pd

# 构造原始DataFrame
data = [
    ["aaaa", 0, "xxx", "yyy", 1, 0, 1],
    ["aaaa", 0, "xxx", "yyy", 2, 0, 0],
    ["aaaa", 0, "xxx", "yyy", 3, 1, 0],
    ["aaaa", 0, "xxx", "yyy", 4, 0, 0],
    ["aaaa", 1, "xxx", "yyy", 5, 0, 0],
    ["aaaa", 1, "xxx", "yyy", 6, 1, 0],
    ["aaaa", 1, "xxx", "yyy", 7, 1, 0],
    ["aaaa", 1, "xxx", "yyy", 8, 0, 1],
    ["bbbb", 0, "xxx", "yyy", 1, 0, 0],
    ["bbbb", 0, "xxx", "yyy", 2, 0, 0],
    ["bbbb", 0, "xxx", "yyy", 3, 0, 0],
    ["bbbb", 0, "xxx", "yyy", 4, 0, 0],
    ["bbbb", 1, "xxx", "yyy", 5, 0, 0],
    ["bbbb", 1, "xxx", "yyy", 6, 0, 0],
    ["bbbb", 1, "xxx", "yyy", 7, 1, 0],
    ["bbbb", 1, "xxx", "yyy", 8, 0, 1],
]
df = pd.DataFrame(data, columns=["Ref1", "EvnNo", "P1", "P2", "Seq", "PP1", "PP2"])

def analyze_group(group):
    # 筛选分组内有1的行
    has_one = group[(group["PP1"] == 1) | (group["PP2"] == 1)]
    if has_one.empty:
        return {"first_p1": 0, "first_p2": 0, "second_p1": 0, "second_p2": 0}
    
    # 确定首次出现1的列
    first_row = has_one.iloc[0]
    first_col = "PP1" if first_row["PP1"] == 1 else "PP2"
    
    # 统计首次出现类型
    first_p1 = 1 if first_col == "PP1" else 0
    first_p2 = 1 if first_col == "PP2" else 0
    
    # 筛选首次出现后的行,统计另一列的1数量
    after_first = group[group["Seq"] > first_row["Seq"]]
    target_col = "PP2" if first_col == "PP1" else "PP1"
    second_count = after_first[after_first[target_col] == 1].shape[0]
    
    # 分配到对应统计项
    second_p1 = second_count if target_col == "PP1" else 0
    second_p2 = second_count if target_col == "PP2" else 0
    
    return {"first_p1": first_p1, "first_p2": first_p2, "second_p1": second_p1, "second_p2": second_p2}

# 分组计算并求和,重命名列
result = df.groupby(["Ref1", "EvnNo"]).apply(analyze_group).apply(pd.Series).sum().to_frame().T
result.columns = ["P1 First Occ", "P2 First Occ", "P1 Second Occ", "P2 Second Occ"]
print(result)

代码说明

  1. 构造数据:将原始数据转换为Pandas DataFrame。
  2. 自定义分析函数:
    • 先筛选分组内包含1的行,若无则返回全0结果。
    • 定位首次出现1的列,标记首次出现的类型。
    • 筛选首次出现后的行,只统计另一列中1的数量。
  3. 分组统计:按Ref1和EvnNo分组应用函数,对各组结果求和后重命名列,得到最终统计表格。

运行代码后输出与预期一致:

P1 First OccP2 First OccP1 Second OccP2 Second Occ
02101

内容的提问来源于stack exchange,提问作者Andy

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.16 10:27:49