Sure I could write this myself, but before I go reinventing the wheel is there a function that already does this?
Sure I could write this myself, but before I go reinventing the wheel is there a function that already does this?
I would suggest another arguably cleaner solution. If X is a datetime.datetime.now() instance, then the quarter is:
import math
Q=math.ceil(X.month/3.)
ceil has to be imported from math module as it can't be accessed directly.
This is very simple and works in python3:
from datetime import datetime
# Get current date-time.
now = datetime.now()
# Determine which quarter of the year is now. Returns q1, q2, q3 or q4.
quarter_of_the_year = f'q{(now.month-1)//3+1}'
For those, who are looking for financial year quarter data, using pandas,
import datetime
import pandas as pd
today_date = datetime.date.today()
quarter = pd.PeriodIndex(today_date, freq='Q-MAR').strftime('Q%q')
reference: pandas period index
This method works for any mapping:
month2quarter = {
1:1,2:1,3:1,
4:2,5:2,6:2,
7:3,8:3,9:3,
10:4,11:4,12:4,
}.get
We have just generated a function int->int
month2quarter(9) # returns 3
This method is also fool-proof
month2quarter(-1) # returns None
month2quarter('July') # returns None
Here is an example of a function that gets a datetime.datetime object and returns a unique string for each quarter:
from datetime import datetime, timedelta
def get_quarter(d):
return "Q%d_%d" % (math.ceil(d.month/3), d.year)
d = datetime.now()
print(d.strftime("%Y-%m-%d"), get_q(d))
d2 = d - timedelta(90)
print(d2.strftime("%Y-%m-%d"), get_q(d2))
d3 = d - timedelta(180 + 365)
print(d3.strftime("%Y-%m-%d"), get_q(d3))
And the output is:
2019-02-14 Q1_2019
2018-11-16 Q4_2018
2017-08-18 Q3_2017
I tried the solution with x//3+1 and x//4+1, We get incorrect quarter in either case. The correct answer is like this
for i in range(1,13):
print(((i-1)//3)+1)
import datetime
def get_quarter_number_and_date_from_choices(p_quarter_choice):
"""
:param p_quarter_choice:
:return:
"""
current_date = datetime.date.today()
# current_quarter = current_date.month - 1 // 3 + 1
if p_quarter_choice == 'Q1':
quarter = 1
q_start_date = datetime.datetime(current_date.year, 3 * quarter - 2, 1)
q_end_date = datetime.datetime(current_date.year, 3 * quarter + 1, 1) + datetime.timedelta(days=-1)
return q_start_date, q_end_date
elif p_quarter_choice == 'Q2':
quarter = 2
q_start_date = datetime.datetime(current_date.year, 3 * quarter - 2, 1)
q_end_date = datetime.datetime(current_date.year, 3 * quarter + 1, 1) + datetime.timedelta(days=-1)
return q_start_date, q_end_date
elif p_quarter_choice == 'Q3':
quarter = 3
q_start_date = datetime.datetime(current_date.year, 3 * quarter - 2, 1)
q_end_date = datetime.datetime(current_date.year, 3 * quarter + 1, 1) + datetime.timedelta(days=-1)
return q_start_date, q_end_date
elif p_quarter_choice == 'Q4':
quarter = 4
q_start_date = datetime.datetime(current_date.year, 3 * quarter - 2, 1)
q_end_date = datetime.datetime(current_date.year, 3 * quarter, 1) + datetime.timedelta(days=30)
return q_start_date, q_end_date
return None
using dictionaries, you can pull this off by
def get_quarter(month):
quarter_dictionary = {
"Q1" : [1,2,3],
"Q2" : [4,5,6],
"Q3" : [7,8,9],
"Q4" : [10,11,12]
}
for key,values in quarter_dictionary.items():
for value in values:
if value == month:
return key
print(get_quarter(3))
A revisited solution using @Alex Martelli formula and creting a quick function as the question asks.
from datetime import timedelta, date
date_from = date(2021, 1, 1)
date_to = date(2021, 12, 31)
get_quarter = lambda dt: (dt.month-1)//3 + 1
quarter_from = get_quarter(date_from)
quarter_to = get_quarter(date_to)
print(quarter_from)
print(quarter_to)
# 1
# 4
def euclid(a,b):
r = a % b
q = int( ( (a + b - 1) - (a - 1) % b ) / b )
return(q,r)
months_per_year = 12
months_per_quarter = 3
for i in range(months_per_year):
print(i+1,euclid(i+1,months_per_quarter)[0])
#1 1
#2 1
#3 1
#4 2
#5 2
#6 2
#7 3
#8 3
#9 3
#10 4
#11 4
#12 4