Given a particular date, say 2011-07-02, how can I find the date of the next Monday (or any weekday day for that matter) after that date?
Answers:
Thank you for visiting the Q&A section on Magenaut. Please note that all the answers may not help you solve the issue immediately. So please treat them as advisements. If you found the post helpful (or not), leave a comment & I’ll get back to you as soon as possible.
Method 1
import datetime
def next_weekday(d, weekday):
days_ahead = weekday - d.weekday()
if days_ahead <= 0: # Target day already happened this week
days_ahead += 7
return d + datetime.timedelta(days_ahead)
d = datetime.date(2011, 7, 2)
next_monday = next_weekday(d, 0) # 0 = Monday, 1=Tuesday, 2=Wednesday...
print(next_monday)
Method 2
Here’s a succinct and generic alternative to the slightly weighty answers above.
def onDay(date, day):
"""
Returns the date of the next given weekday after
the given date. For example, the date of next Monday.
NB: if it IS the day we're looking for, this returns 0.
consider then doing onDay(foo, day + 1).
"""
days = (day - date.weekday() + 7) % 7
return date + datetime.timedelta(days=days)
Method 3
Try
>>> dt = datetime(2011, 7, 2) >>> dt + timedelta(days=(7 - dt.weekday())) datetime.datetime(2011, 7, 4, 0, 0)
using, that the next monday is 7 days after the a monday, 6 days after a tuesday, and so on, and also using, that Python’s datetime type reports monday as 0, …, sunday as 6.
Method 4
This is example of calculations within ring mod 7.
import datetime
def next_day(given_date, weekday):
day_shift = (weekday - given_date.weekday()) % 7
return given_date + datetime.timedelta(days=day_shift)
now = datetime.date(2018, 4, 15) # sunday
names = ['monday', 'tuesday', 'wednesday', 'thursday', 'friday',
'saturday', 'sunday']
for weekday in range(7):
print(names[weekday], next_day(now, weekday))
will print:
monday 2018-04-16 tuesday 2018-04-17 wednesday 2018-04-18 thursday 2018-04-19 friday 2018-04-20 saturday 2018-04-21 sunday 2018-04-15
As you see it’s correctly give you next monday, tuesday, wednesday, thursday friday and saturday. And it also understood that 2018-04-15 is a sunday and returned current sunday instead of next one.
I’m sure you’ll find this answer extremely helpful after 7 years 😉
Method 5
Another simple elegant solution is to use pandas offsets.
I find it very helpful and robust when playing with dates.
- If you want the first Sunday just modify the frequency to freq=’W-SUN’.
- If you want a couple of next Sundays, change the offsets.Day(days).
- Using pandas offsets allow you to ignore holidays, work only with Business Days and more.
You can also apply this method easily on a whole DataFrame using the apply method.
import pandas as pd
import datetime
# 1. Getting the closest monday from a given date
date = datetime.date(2011, 7, 2)
closest_monday = pd.date_range(start=date, end=date + pd.offsets.Day(6), freq="W-MON")[
0
]
# 2. Adding a 'ClosestMonday' column with the closest monday for each row in
# a pandas df using apply. Requires you to have a 'Date' column in your df
def get_closest_monday(row):
return pd.date_range(
start=row.Date, end=row.Date + pd.offsets.Day(6), freq="W-MON"
)[0]
df = pd.DataFrame([datetime.date(2011, 7, 2)], columns=["Date"])
df["ClosestMonday"] = df.apply(lambda row: get_closest_monday(row), axis=1)
print(df)
Method 6
Another alternative uses rrule
from dateutil.rrule import rrule, WEEKLY, MO from datetime import date next_monday = rrule(freq=WEEKLY, dtstart=date.today(), byweekday=MO, count=1)[0]
rrule docs: https://dateutil.readthedocs.io/en/stable/rrule.html
Method 7
You can start adding one day to date object and stop when it’s monday.
>>> d = datetime.date(2011, 7, 2) >>> while d.weekday() != 0: #0 for monday ... d += datetime.timedelta(days=1) ... >>> d datetime.date(2011, 7, 4)
Method 8
import datetime
d = datetime.date(2011, 7, 2)
while d.weekday() != 0:
d += datetime.timedelta(1)
Method 9
weekday = 0 ## Monday dt = datetime.datetime.now().replace(hour=0, minute=0, second=0) ## or any specific date days_remaining = (weekday - dt.weekday() - 1) % 7 + 1 next_dt = dt + datetime.timedelta(days_remaining)
Method 10
Generally to find any date from day of week from today:
def getDateFromDayOfWeek(dayOfWeek):
week_days = ["monday", "tuesday", "wednesday",
"thursday", "friday", "saturday", "sunday"]
today = datetime.datetime.today().weekday()
requiredDay = week_days.index(dayOfWeek)
if today>requiredDay:
noOfDays=7-(today-requiredDay)
print("noDays",noOfDays)
else:
noOfDays = requiredDay-today
print("noDays",noOfDays)
requiredDate = datetime.datetime.today()+datetime.timedelta(days=noOfDays)
return requiredDate
print(getDateFromDayOfWeek('sunday').strftime("%d/%m/%y"))
Gives output in format of Day/Month/Year
Method 11
dateutil has a special feature for this kind of operation and it’s the most elegant way I have ever seen yet.
from datetime import datetime from dateutil.relativedelta import relativedelta, MO first_monday_date = (datetime(2011,7,2) + relativedelta(weekday=MO(0))).date()
if you want datetime just
first_monday_date = datetime(2011,7,2) + relativedelta(weekday=MO(0))
Method 12
This will give the first next Monday after given date:
import datetime
def get_next_monday(year, month, day):
date0 = datetime.date(year, month, day)
next_monday = date0 + datetime.timedelta(7 - date0.weekday() or 7)
return next_monday
print get_next_monday(2011, 7, 2)
print get_next_monday(2015, 8, 31)
print get_next_monday(2015, 9, 1)
2011-07-04
2015-09-07
2015-09-07
Method 13
via list comprehension?
from datetime import * [datetime.today()+timedelta(days=x) for x in range(0,7) if (datetime.today()+timedelta(days=x)).weekday() % 7 == 0] (0 at the end is for next monday, returns current date when run on monday)
All methods was sourced from stackoverflow.com or stackexchange.com, is licensed under cc by-sa 2.5, cc by-sa 3.0 and cc by-sa 4.0