I\'m trying to find last business day of of the month. I wrote the code below for that and it works fine but I was wondering if there is a cleaner way of doing it?
You can use Pandas
to get business days. Refer http://pandas.pydata.org/pandas-docs/stable/timeseries.html
Also you can refer this https://pypi.python.org/pypi/business_calendar/ for simple business days calculation.
I use this for the first business day of the month but it can be used for last business day of the month as well:
import time
import datetime
from pandas.tseries.holiday import USFederalHolidayCalendar
from pandas.tseries.offsets import CustomBusinessDay
from dateutil.relativedelta import relativedelta
#Create dates needed to be entered as parameters
today = datetime.date.today()
first = today.replace(day=1)
#End of the Prior Month
eopm = first - datetime.timedelta(days=1)
eopm = eopm.strftime("%Y%m%d")
#Create first business day of current month date
us_bd = CustomBusinessDay(calendar=USFederalHolidayCalendar())
focm = first
nxtMo = today + relativedelta(months=+1)
fonm = nxtMo.replace(day=1)
eocm = fonm - datetime.timedelta(days=1)
first_bd = pd.DatetimeIndex(start = focm, end = eocm, freq= us_bd)
first_bd = first_bd.strftime("%Y%m%d")
#First Business Day of the Month
first_bd = first_bd[0]
#Last Business Day of the Month
lst_day = len(first_bd)-1
last_bd = first_bd[lst_day]
I left some code in there that is not needed for the last business day of the current month, but may be useful to someone.
Let's say you want to get the last business days of the month up-to the end of the next two years, the following will work.
import pandas as pd
import datetime
start = datetime.date.today()
end = datetime.date(start.year+2, 12, 31)
bussiness_days_rng =pd.date_range(start, end, freq='BM')
with rollforward(d) you will skip to the next month if the date is past the last business day of the current month, so below might be safer for any day of the month:
from datetime import date
import pandas as pd
d = date(2011, 12, 31) # a caturday
pd.bdate_range(end=pd.offsets.MonthEnd().rollforward(d), periods=1)
pd.offsets.BMonthEnd().rollforward(d)
For one-liner fans:
import calendar
def last_business_day_in_month(year: int, month: int) -> int:
return max(calendar.monthcalendar(year, month)[-1:][0][:5])
I use the following:
from pandas.tseries.offsets import BMonthEnd
from datetime import date
d=date.today()
offset = BMonthEnd()
#Last day of current month
offset.rollforward(d)
#Last day of previous month
offset.rollback(d)