'Python get months start and end dates for a given year
I want to write a python function to get months start and end dates for a given year.
Sample Input : 2021
Expected output :
[(01-Jan-2021,31-Jan-2021), (01-Feb-2021,28-Feb-2021), (01-Mar-2021,31-Mar-2021), etc..)]
Solution 1:[1]
The end date is a trickier part here since it can be either 28
, 29
, 30
or 31
,.
You can use the isleap
functionality from the calendar
module:
from calendar import isleap
import datetime
year = 2024
months_choices = []
for i in range(1, 13):
month = datetime.date(2021, i, 1).strftime('%b')
startDate = f"01-{month}-{year}"
if month in ["Jan", "Mar", "May", "Jul", "Aug", "Oct", "Dec"]:
endDate = f"31-{month}-{year}"
elif month in ["Apr", "Jun", "Sep", "Nov"]:
endDate = f"30-{month}-{year}"
else:
isLeap = isleap(1900)
if isLeap:
endDate = f"29-{month}-{year}"
else:
endDate = f"28-{month}-{year}"
months_choices.append((startDate, endDate))
print(months_choices)
Output (for a leap
year):
[('01-Jan-2024', '31-Jan-2024'), ('01-Feb-2024', '29-Feb-2024'), ('01-Mar-2024', '31-Mar-2024'), ('01-Apr-2024', '30-Apr-2024'), ('01-May-2024', '31-May-2024'), ('01-Jun-2024', '30-Jun-2024'), ('01-Jul-2024', '31-Jul-2024'), ('01-Aug-2024', '31-Aug-2024'), ('01-Sep-2024', '30-Sep-2024'), ('01-Oct-2024', '31-Oct-2024'), ('01-Nov-2024', '30-Nov-2024'), ('01-Dec-2024', '31-Dec-2024')]
Solution 2:[2]
you can use pandas
date ranges, with appropriate frequency alias for month start and month end. Ex:
import pandas as pd
year, nMonths = "2020", 12
monthStart = pd.date_range(year, periods=nMonths, freq='MS').strftime("%d-%b-%Y")
monthEnd = pd.date_range(year, periods=nMonths, freq='M').strftime("%d-%b-%Y")
l = [(s,e) for s,e in zip(monthStart, monthEnd)]
l
[('01-Jan-2020', '31-Jan-2020'),
('01-Feb-2020', '29-Feb-2020'),
('01-Mar-2020', '31-Mar-2020'),
('01-Apr-2020', '30-Apr-2020'),
('01-May-2020', '31-May-2020'),
('01-Jun-2020', '30-Jun-2020'),
('01-Jul-2020', '31-Jul-2020'),
('01-Aug-2020', '31-Aug-2020'),
('01-Sep-2020', '30-Sep-2020'),
('01-Oct-2020', '31-Oct-2020'),
('01-Nov-2020', '30-Nov-2020'),
('01-Dec-2020', '31-Dec-2020')]
Solution 3:[3]
You're literally just checking if a year is a leap and then determining the length of Feb. This is probably a simple way of doing it:
import calendar
def MonthsStartAndEnd(year):
# create dictionary of normal month lengths
months = {
'Jan': '31',
'Feb': '28',
'Mar': '31',
'Apr': '30',
'May': '31',
'Jun': '30',
'Jul': '31',
'Aug': '31',
'Sep': '30',
'Oct': '31',
'Nov': '30',
'Dec': '31'
}
# check if the year is leap and if so update Feb to 29 days
if calendar.isleap(year):
months['Feb'] = '29'
# return the formatted list of values
return [f"01-{key}-{year},{value}-{key}-{year}" for key, value in months.items()]
print(MonthsStartAndEnd(2000))
print(MonthsStartAndEnd(2001))
#['01-Jan-2000,31-Jan-2000', '01-Feb-2000,29-Feb-2000', '01-Mar-2000,31-Mar-2000', '01-Apr-2000,31-Apr-2000', '01-May-2000,31-May-2000', '01-Jun-2000,31-Jun-2000', '01-Jul-2000,31-Jul-2000', '01-Aug-2000,31-Aug-2000', '01-Sep-2000,31-Sep-2000', '01-Oct-2000,31-Oct-2000', '01-Nov-2000,31-Nov-2000', '01-Dec-2000,31-Dec-2000']
['01-Jan-2001,31-Jan-2001', '01-Feb-2001,28-Feb-2001', '01-Mar-2001,31-Mar-2001', '01-Apr-2001,31-Apr-2001', '01-May-2001,31-May-2001', '01-Jun-2001,31-Jun-2001', '01-Jul-2001,31-Jul-2001', '01-Aug-2001,31-Aug-2001', '01-Sep-2001,31-Sep-2001', '01-Oct-2001,31-Oct-2001', '01-Nov-2001,31-Nov-2001', '01-Dec-2001,31-Dec-2001']
Solution 4:[4]
If you are using Pandas, period_range is best suited for this (no zipping date series required!):
import pandas as pd
periods = pd.period_range('1/1/2016', freq='M', periods=12)
print([(p.start_time.strftime('%d-%b-%Y'), p.end_time.strftime('%d-%b-%Y')) for p in periods])
# outputs: [('01-Jan-2016', '31-Jan-2016'), ('01-Feb-2016', '29-Feb-2016'), ...]
All pandas date/time functionality can be found here: https://pandas.pydata.org/pandas-docs/stable/user_guide/timeseries.html#
Sources
This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.
Source: Stack Overflow
Solution | Source |
---|---|
Solution 1 | Krishna Chaurasia |
Solution 2 | |
Solution 3 | |
Solution 4 | Bemis |