【问题标题】:How do I compensate holidays - pandas我如何补偿假期 - 熊猫
【发布时间】:2019-09-29 04:39:29
【问题描述】:

假设我有一个如下的数据框:

df = pd.DataFrame({'Ending Date': [Timestamp('2019-12-08 00:00:00'), Timestamp('2019-12-08 00:00:00')], 'FName': ['Jon', 'Bob'], 'LName': ['Doe', 'Smith'], 'Starting Date': ['2019-09-29', '2019-09-29']})

  Ending Date FName  LName Starting Date
0  2019-12-07   Jon    Doe    2019-09-28
1  2019-12-07   Bob  Smith    2019-09-28

如您所见,结束日期列总是比开始日期早 10 周,但是,我有一个假期列表:

holidays = pd.Series([Timestamp('2019-09-14 00:00:00'), Timestamp('2019-10-05 00:00:00'), Timestamp('2019-10-12 00:00:00'), Timestamp('2019-10-26 00:00:00'), Timestamp('2019-12-21 00:00:00'), Timestamp('2019-12-28 00:00:00'), Timestamp('2020-01-04 00:00:00'), Timestamp('2020-01-25 00:00:00'), Timestamp('2020-02-01 00:00:00'), Timestamp('2020-02-29 00:00:00'), Timestamp('2020-04-04 00:00:00'), Timestamp('2020-05-02 00:00:00')])

因此,我想“补偿”假期,所以我想计算假期系列中开始日期和结束日期之间范围的每个星期六,并添加 n(计数)周到结束日期,如果增加的任何一周是假期,也要补偿它们,依此类推...

我试过了:

df['Ending Date'] = df['Ending Date'] + pd.Timedelta(weeks=10 + pd.date_range(df['Starting Date'], df['Ending Date']).isin(holidays).sum())

但是一个错误:

TypeError: Cannot convert input [0    2019-09-28
1    2019-09-28
Name: Starting Date, dtype: object] of type <class 'pandas.core.series.Series'> to Timestamp

被提升了。

期望的输出:

  Ending Date FName  LName Starting Date
0  2020-01-18   Jon    Doe    2019-09-28
1  2020-01-18   Bob  Smith    2019-09-28

【问题讨论】:

  • 这里的预期输出是什么?
  • 您可以只使用pandas(参见doc)中的工作日计算而不是自己进行计算吗?
  • @jezrael 你能找到答案吗?
  • @jezrael 让我向您展示循环,因此从 9 月 28 日开始的 10 周到 12 月 7 日,但在该范围内,它包含三个假期,因此结束日期应该延长 3 周,那么将是 12 月 28 日,但是范围内还有两个新的假期,所以结束日期应该延长两周,1 月 11 日,然后又增加了一个假期,所以加上一周将是 1 月 18 日,得到现在呢?
  • @jezrael 60 左右,我不介意表演

标签: python pandas datetime date-range


【解决方案1】:

我假设 Starting DateEnding Date 都应该是 datetime64[ns] 类型。如果不是,请使用 pd.to_datetime 进行转换。

我注意到您只使用星期六日期,所以您的情况类似于 我们有一个工作周,一个日历周中只有一个工作日, 即只有星期六。

那么,完成你的任务,如果我们使用自定义业务是很容易的 日历,带有用户定义的假期日期。

从定义 CustomBusinessDay 偏移开始,包括您的假期列表:

my_bday = pd.offsets.CustomBusinessDay(holidays=holidays, weekmask='Sat')

然后,计算提前 n 个工作日(实际上是几周)的日期 从给定日期dat,我们应该使用公式:dat + 10 * my_bday

所以在你的情况下(开始日期列中的源数据和结果是 保存在结束日期),运行:

df['Ending Date'] = df['Starting Date'].apply(lambda dat: dat + 10 * my_bday)

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2023-03-26
    • 1970-01-01
    • 2020-03-15
    • 2019-05-08
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多