find the last business date for June and Dec of any given year in Python - python-3.x

I want to find the last business day for the month of June and Dec for 2019. my below code gives me the last business day for last month and the current month. Ideally i want a code which allows me to input a year and month and it will tell me the last business day for the month and year i input.
i want my output to be like this for June 2019 and Dec 2019
2906
3112
hope someone can help me here, thanks
from pandas.tseries.offsets import BMonthEnd
from datetime import date
d=date.today()
offset = BMonthEnd()
#Last day of current month
current_month = offset.rollforward(d)
print(current_month)
#Last day of previous month
last_month = offset.rollback(d)
print(last_month)

Here's a function that will find the last weekday in a given month and format it as a string in the format given
import datetime
def last_weekday(year, month):
# Add a month
if month == 12:
month = 1
year += 1
else:
month += 1
d = datetime.date(year, month, 1)
# Subtract a day
d -= datetime.timedelta(days=1)
# Subtract more days if we have a weekend
while d.weekday() >= 5:
d -= datetime.timedelta(days=1)
return '{:02d}{:02d}'.format(d.month, d.day)
# Examples:
last_weekday(2019, 6) # -> '0628'
last_weekday(2019, 12) # -> '1231'

Related

using week number to get range of dates with sunday as first day of week in python

input: week_number = 34 (or 2022-34)
expected output:
["2022-08-21","2022-08-22", "2022-08-23","2022-08-24","2022-08-25","2022-08-26","2022-08-27"]
First date should be of Sunday
the last date should be Saturday
work with both leap and non leap year
Try:
import datetime
week_number = 34
out = []
date = datetime.datetime.strptime(f"2022-{week_number}-0", "%Y-%U-%w")
for day in range(7):
out.append((date + datetime.timedelta(days=day)).strftime("%Y-%m-%d"))
print(out)
Prints:
[
"2022-08-21",
"2022-08-22",
"2022-08-23",
"2022-08-24",
"2022-08-25",
"2022-08-26",
"2022-08-27",
]
From the reference:
%U - Week number of the year (Sunday as the first day of the week) as
a zero-padded decimal number. All days in a new year preceding the
first Sunday are considered to be in week 0.

Python3 Get epoch time first and last day of month

Given a month and a year, such as 03 2022, I need to get the epoch time of the first day of the month and the last day of the month. I am not sure how to do that. Any help would be appreciated. Thank you.
You can get the beginning of the month easily by setting the day to 1.
To get the end of the month conveniently, you can calculate the first day of the next month, then go back one day.
Then set the time zone (tzinfo) to UTC to prevent Python using local time.
Finally a call to .timestamp()
import datetime
def date_to_endofmonth(
dt: datetime.datetime, offset: datetime.timedelta = datetime.timedelta(days=1)
) -> datetime.datetime:
"""
Roll a datetime to the end of the month.
Parameters
----------
dt : datetime.datetime
datetime object to use.
offset : datetime.timedelta, optional.
Offset to the next month. The default is 1 day; datetime.timedelta(days=1).
Returns
-------
datetime.datetime
End of month datetime.
"""
# reset day to first day of month, add one month and subtract offset duration
return (
datetime.datetime(
dt.year + ((dt.month + 1) // 12), ((dt.month + 1) % 12) or 12, 1
)
- offset
)
year, month = 2022, 11
# make datetime objects; make sure to set UTC
dt_month_begin = datetime.datetime(year, month, 1, tzinfo=datetime.timezone.utc)
dt_month_end = date_to_endofmonth(dt_month_begin).replace(tzinfo=datetime.timezone.utc)
ts_month_begin = dt_month_begin.timestamp()
ts_month_end = dt_month_end.timestamp()
print(ts_month_begin, ts_month_end)
# 1667260800.0 1701302400.0
Unable to comment due to reputation but #FObersteiner is excellent just I would recommend a small change.
For example running the current code it would produce this for Nov 2022
print(dt_month_begin.timestamp())
print(dt_month_begin)
print(dt_month_end.timestamp())
print(dt_month_end)
--->
1667260800.0
2022-11-01 00:00:00+00:00
1701302400.0
2023-11-30 00:00:00+00:00
Note the year field
I'd suggest the following
import datetime
def date_to_endofmonth(
dt: datetime.datetime, offset: datetime.timedelta = datetime.timedelta(seconds=1)
) -> datetime.datetime:
"""
Roll a datetime to the end of the month.
Parameters
----------
dt : datetime.datetime
datetime object to use.
offset : datetime.timedelta, optional.
Offset to the next month. The default is 1 second; datetime.timedelta(seconds=1).
Returns
-------
datetime.datetime
End of month datetime.
"""
# reset day to first day of month, add one month and subtract offset duration
return (
datetime.datetime(
dt.year + ((dt.month + 1) // 13), ((dt.month + 1) % 12) or 12, 1
)
- offset
)
year, month = 2022, 11
# make datetime objects; make sure to set UTC
dt_month_begin = datetime.datetime(year, month, 1, tzinfo=datetime.timezone.utc)
dt_month_end = date_to_endofmonth(dt_month_begin).replace(tzinfo=datetime.timezone.utc)
Differences being floor division by 13 instead of 12 to handle the month of November.
Changing the offset to seconds delta because I felt the user ( and myself who came looking for the answer) wanted the starting epoch time and the ending epoch time so
Nov 1st 00:00:00 --> Nov 30th 23:59:59 would be better than
Nov 1st 00:00:00 --> Nov 30th 00:00:00 ( Losing a day worth of seconds)
Output of the above would be
:
1667260800.0
2022-11-01 00:00:00+00:00
1669852799.0
2022-11-30 23:59:59+00:00

How to get Monday and Sunday of last week

If today is November 28, 2021, I want to get last week's Monday and Sunday like:
Monday: 2021-11-15
Sunday: 2021-11-21
I tried like this:
today = datetime.date.today()
idx = (today.weekday() + 1) % 7
self.monday = (today - datetime.timedelta(7 + idx - 1)).strftime('%Y-%m-%d')
self.sunday = (today - datetime.timedelta(7 + idx - 7)).strftime('%Y-%m-%d')
But the output is like this, which is wrong:
Monday: 2021-11-22
Sunday: 2021-11-28
It is correct if today's date is November 29, 2021.
How will I be able to achieve this?
Take today's date and subtract 1 week plus today's weekday 'number':
today = datetime.date.today()
today - datetime.timedelta(days=today.weekday(), weeks=1)
For the Sunday before that, use days=today.weekday() + 1

Pandas to recognize current date, and filter a date column relative to today's date

Having a lot of trouble translating the logic below in pandas/python, so I do not even have sample code or a df to work with :x
I run a daily report, that essentially filters for data from Monday thru the day before what 'Today' is. I have a Date column [ in dt.strftime('%#m/%#d/%Y') format] . It will never be longer than a Monday-Sunday scope.
1) Recognize the day it is 'today' when running the report, and recognize what day the closet Monday prior was. Filter the "Date" Column for the Monday-day before today's date [ in dt.strftime('%#m/%#d/%Y') format ]
2) Once the df is filtered for that, take this group of rows that have dates in the logic above, have it check for dates in a new column "Date2". If any dates are before the Monday Date, in Date2, change all of those earlier dates in 'Date2' to the Monday date it the 'Date' column.
3) If 'Today' is a Monday, then filter the scope from the Prior Monday through - Sunday in the "Date" Column. While this is filtered, do the step above [step 2] but also, for any dates in the "Date2" column that are Saturday and Sunday Dates - changes those to the Friday date.
Does this make sense?
Here're the steps:
from datetime import datetime
today = pd.to_datetime(datetime.now().date())
day_of_week = today.dayofweek
last_monday = today - pd.to_timedelta(day_of_week, unit='d')
# if today is Monday, we need to step back another week
if day_of_week == 0:
last_monday -= pd.to_timedelta(7, unit='d')
# filter for last Monday
last_monday_flags = (df.Date == last_mon)
# filter for Date2 < last Monday
date2_flags = (df.Date2 < last_monday)
# update where both flags are true
flags = last_monday_flags & date2_flags
df.loc[flags, 'Date2'] = last_monday
# if today is Monday
if day_of_week == 0:
last_sunday = last_monday + pd.to_timedelta(6, unit='d')
last_sat = last_sunday - pd.to_timedelta(1, unit='d')
last_week_flags = (df.Date >= last_monday) & (df.Date <= next_sunday)
last_sat_flags = (df.Date2 == last_sat)
last_sun_flags = (df.Date2 == last_sun)
# I'm just too lazy and not sure how Sat and Sun relates to Fri
# but i guess just subtract 1 day or 2 depending on which day
...

ValueError: day is out of range for month python

I am writing code that lets users write down dates and times for things they have on. It takes in the date on which it starts, the start time and finish time. It also allows the user to specify if they want it to carry over into multiple weeks (every Monday for a month for example)
I am using a for loop to do this, and because of the different months having different days I obviously want (if the next Monday for example is in the next month) it to have the correct date.
This is my code:
for i in range(0 , times):
day = day
month = month
fulldateadd = datetime.date(year, month, day)
day = day + 7
if month == ( '01' or '03' or '05' or '07' or '10'or '12'):
if day > 31:
print(day)
day = day - 31
print(day)
month = month + 1
elif month == ( '04' or '06'or '09' or '11'):
if day > 30:
print(day)
day = day - 30
print(day)
month = month + 1
elif month == '02':
if day > 29:
print(day)
day = day - 29
print(day)
month = month + 1
When running this and testing to see if it goes correctly into the new month I get the error:
File "C:\Users\dansi\AppData\Local\Programs\Python\Python36-32\gui test 3.py", line 73, in addtimeslot
fulldateadd = datetime.date(year, month, day)
ValueError: day is out of range for month
Where have I gone wrong?
It's hard to be completely accurate without seeing some of the previous code (for example, where do day, month, year, and times come from?), but here's how you might be able to use timedelta in your code:
fulldateadd = datetime.date(year, month, day)
for i in range(times):
fulldateadd = fulldateadd + datetime.timedelta(7)
A timedelta instance represents a period of time, rather than a specific absolute time. By default, a single integer passed to the constructor represents a number of days. So timedelta(7) gives you an object that represents 7 days.
timedelta instances can then be used with datetime or date instances using basic arithmetic. For example, date(2016, 12, 31) + timedelta(1) would give you date(2017, 1, 1) without you needing to do anything special.

Resources