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

如何用groupby()与for loop统计满足日期条件的空值记录数

需求实现:按月份统计符合条件的记录数

数据生成代码

import pandas as pd
import numpy as np
from datetime import timedelta
import random  # 补充原代码遗漏的导入

random.seed(365)

# 生成数据
start_date = pd.date_range(start="2015-01-09", end="2022-09-11", freq="6D")
end_date = [date + timedelta(days=np.random.exponential(scale=100)) for date in start_date]
df = pd.DataFrame(
    {"start_date": start_date,
     "end_date": end_date}
)
# 随机移除部分end_date值
df["end_date"] = df["end_date"].sample(frac=0.7).reset_index(drop=True)
df["end_date"] = df["end_date"].dt.date.astype("datetime64[ns]")

生成月份第一天序列

dates = pd.Series(df["start_date"].dt.to_period("M").sort_values(ascending=True).unique()).dt.start_time

需求说明

统计每个月份第一天对应的df记录数,需同时满足两个条件:

  • df["start_date"] 小于该月份第一天
  • df["end_date"] 为NaT(空值)

要求用**for loop结合groupby()**实现,输出格式参考:

month_startcount
2015-01-015
2015-02-0110
2015-03-0135

错误尝试代码

df.groupby(by=dates)[["start_date", "end_date"]].apply(
    lambda x: [x["start_date"] < date for date in dates] & x["end_date"].isnull == True
)

正确实现方法

方式1:显式for loop遍历统计

先筛选出end_date为空的记录,再逐个遍历月份第一天统计符合条件的数量:

# 先筛选出end_date为空的子集
null_end_df = df[df["end_date"].isnull()]

# 初始化结果存储列表
result_list = []

# 遍历每个月份第一天
for month_start in dates:
    # 统计满足start_date < 当前月份第一天的记录数
    count = null_end_df[null_end_df["start_date"] < month_start].shape[0]
    result_list.append({"month_start": month_start, "count": count})

# 转换为DataFrame并格式化日期
result_df = pd.DataFrame(result_list)
result_df["month_start"] = result_df["month_start"].dt.date.astype("datetime64[ns]")

print(result_df)

输出示例(根据实际数据生成)

month_startcount
2015-01-010
2015-02-015
2015-03-019
......

方式2:groupby结合匹配逻辑(简化循环)

如果想减少显式循环,可通过给空值记录匹配对应月份区间,再分组统计:

null_end_df = df[df["end_date"].isnull()]
# 给每个start_date匹配大于它的最小月份第一天
null_end_df["month_start"] = null_end_df["start_date"].apply(
    lambda x: dates[dates > x].min() if (dates > x).any() else None
)
# 按月份分组统计,补全所有月份(包括count为0的)
result_df = null_end_df.groupby("month_start").size().reindex(dates, fill_value=0).reset_index(name="count")

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.02 15:45:36