pandas 正在检索上一季度的日期

b1zrtrql  于 2023-04-28  发布在  其他
关注(0)|答案(2)|浏览(123)

背景

我正在尝试注入一个有效负载,其中包含最近一个财政季度的日期。

示例

如果今天是4月20日(这是Q2中的一个日期),则最近完成的上一季度将是Q1(即1月1日至3月31日),因此我将向有效负载注入 * start_date: 2022-12-31end_date: 2023-03-31

*请注意start_date始终为季度开始之前的日期;这是正常的做法。
当前编码

# I am currently injecting the current dates into my payload.
# Instead, I am looking for the previous quarter's dates
start_date = dt.datetime.today().strftime("%Y-%m-%d")
end_date = dt.datetime.today().strftime("%Y-%m-%d")
    
    def job_initializer():
        #   calling function that returns variables required for API call
        key, secret, url = authentication()
        payload = """
        {
          "data":{
            "type":"jobs",
            "attributes":{
              "job_type":"portfolio_view_results",
              "parameters":{
                "view_id":"416555",
                "portfolio_type":"firm",
                "portfolio_id":"1",
                "output_type":"csv",
                "start_date":"%s",
                "end_date":"%s"
              }
            }
          }
        }
        """ % (start_date, end_date)

建议

我看到很多10年前的历史帖子,但是我希望这可以使用pandas或其他以时间为中心的python库来实现?

e0bqpujr

e0bqpujr1#

numpy或其他库中可能内置了一些东西,但由于只有四个四分之一,因此没有太多的硬编码:

import datetime
 
today = datetime.date.today()
quarters = [ datetime.date(today.year-1,12,31),
             datetime.date(today.year,3,31),
             datetime.date(today.year,6,30),
             datetime.date(today.year,9,30),
             datetime.date(today.year,12,31) ]
quarter, start_date = [(i,d) for i,d in enumerate(quarters) if d < today][-1]
end_date = quarters[quarter+1]
print(f'{start_date}, {end_date}')
g9icjywg

g9icjywg2#

您可以将季度的开始日期硬编码为datetime对象,例如Mark shows in their answer,将其硬编码为指定年偏移量、月和日的元组。

import datetime as dt

quarters = [(-1, 12, 31), (0, 3, 31), (0, 6, 30), (0, 9, 30), (0, 12, 31)]

给定today = dt.date.today(),该列表中当前季度的开始日期的索引为(today.month - 1 // 3)。结束日期的索引为1加上开始日期索引:

i_start = (today.month - 1) // 3

q_start = dt.datetime(today.year - quarters[i_start][0], *quarters[i_start][1:])
# datetime.datetime(2023, 3, 31, 0, 0)

q_end = dt.datetime(today.year - quarters[i_start + 1][0], *quarters[i_start + 1][1:])
# datetime.datetime(2023, 6, 30, 0, 0)

要在列df["Date"]中包含datetime对象的pandas Dataframe (df)中使用这种方法,回想一下pandas提供了一个Series.dt.quarter,它为任何日期提供i_start + 1。让我们修改quarters,以便我们可以在pandas向量函数中使用它:

quarters_df = pd.DataFrame(quarters, columns=["year_offset", "month", "day"])

quarters_df看起来像这样:

year_offset  month  day
0           -1     12   31
1            0      3   31
2            0      6   30
3            0      9   30
4            0     12   31

然后,您可以执行以下操作:

# Get the index of the quarter start and end date
i_end = df['Date'].dt.quarter
i_start = i_end - 1

# Get those elements from quarters_df, then reset the index to the original dataframe's index
q_start = quarters_df.loc[i_start].set_index(df.index)
# Set year to the date's year plus the year offset
q_start["year"] = q_start["year_offset"] + df["Date"].dt.year

q_end = quarters_df.loc[i_end].set_index(df.index)
q_end["year"] = q_end["year_offset"] + df["Date"].dt.year

**注意:**你也可以使用上面的公式来得到i_starti_end,但是我们有dt.quarter,为什么不使用它:)

i_start = (df["Date"].dt.month - 1) // 3
i_end = i_start + 1

最后,构建datetime列:

df["quarter_start"] = pd.to_datetime(q_start[["year", "month", "day"]])

df["quarter_end"] = pd.to_datetime(q_end[["year", "month", "day"]])

对于以下示例dataframe:

data = [dt.datetime(2003, 6, 4, 0, 0),
 dt.datetime(2015, 6, 22, 0, 0),
 dt.datetime(2000, 10, 9, 0, 0),
 dt.datetime(2023, 11, 23, 0, 0),
 dt.datetime(2011, 2, 7, 0, 0),
 dt.datetime(2009, 7, 27, 0, 0),
 dt.datetime(2005, 12, 23, 0, 0),
 dt.datetime(2018, 2, 4, 0, 0),
 dt.datetime(2019, 9, 28, 0, 0),
 dt.datetime(2004, 2, 21, 0, 0)]

df = pd.DataFrame(data, columns=['Date'])

上面显示的方法为我们提供:

Date quarter_start quarter_end
0 2003-06-04    2003-03-31  2003-06-30
1 2015-06-22    2015-03-31  2015-06-30
2 2000-10-09    2000-09-30  2000-12-31
3 2023-11-23    2023-09-30  2023-12-31
4 2011-02-07    2010-12-31  2011-03-31
5 2009-07-27    2009-06-30  2009-09-30
6 2005-12-23    2005-09-30  2005-12-31
7 2018-02-04    2017-12-31  2018-03-31
8 2019-09-28    2019-06-30  2019-09-30
9 2004-02-21    2003-12-31  2004-03-31

相关问题