Basically, I'm trying to check whether a date, e.g. 2021-07-08, is in the next week, or the week after that, or neither.
#I can call the start and end dates of the current week
start = tday - timedelta(days=tday.weekday())
end = start + timedelta(days=6)
print("Today: " + str(tday))
print("Start: " + str(start))
print("End: " + str(end))
# and I can get the current week number.
curr_week = datetime.date.today().strftime("%V")
print(curr_week)
Is there a better way than getting a list of dates in curr_week + 1 and then checking whether date is in in that list?
Thanks so much
GENERAL ANSWER
It is best to stick to datetime and timedelta, since this handles all edge cases like year changes, years with 53 weeks etc.
So find the number of the next week, and compare the weeknumber of the week you want to check against that.
import datetime
# Date to check in date format:
check_date = datetime.datetime.strptime("2021-09-08", "%Y-%d-%m").date()
# Current week number:
curr_week = datetime.date.today().strftime("%V")
# number of next week
next_week = (datetime.date.today()+datetime.timedelta(weeks=1)).strftime("%V")
# number of the week after that
week_after_next_week = (datetime.date.today()+datetime.timedelta(weeks=2)).strftime("%V")
# Compare week numbers of next weeks to the week number of the date to check:
if next_week == check_date.strftime("%V"):
# Date is within next week, put code here
pass
elif week_after_next_week == check_date.strftime("%V"):
# Date is the week after next week, put code here
pass
OLD ANSWER
This messes up around year changes, and modulo doesn't fix it because there are years with 53 weeks.
You can compare the week numbers by converting them to integers. You don't need to create a list of all dates within the next week.
import datetime
# Date to check in date format:
check_date = datetime.datetime.strptime("2021-07-08", "%Y-%d-%m").date()
# Current week number, make it modulo so that the last week is week 0:
curr_week = int(datetime.date.today().strftime("%V"))
# Compare week numbers:
if curr_week == (int(check_date.strftime("%V"))-1):
# Date is within next week, put code here
pass
elif curr_week == (int(check_date.strftime("%V"))-2):
# Date is the week after next week, put code here
pass
You can cast the date you want to check in datetime, and then compare the week numbers.
# date you want to check
date = datetime.datetime.strptime("2021-07-08","%Y-%m-%d")
# current date
tday = datetime.date.today()
# compare the weeks
print(date.strftime("%V"))
print(tday.strftime("%V"))
27
32
[see Alfred's answer]
You can get the week number directly as an integer integer from the IsoCalendarDate representation of each date.
from datetime import datetime
date_format = '%Y-%m-%d'
t_now = datetime.strptime('2021-08-11', date_format)
target_date = datetime.strptime('2021-08-18', date_format)
Just using datetime comparing:
from datetime import datetime, timedelta
def in_next_week(date):
""" -1: before; 0: in; 1: after next week;"""
today = datetime.today()
this_monday = today.date() - timedelta(today.weekday())
start = this_monday + timedelta(weeks=1)
end = this_monday + timedelta(weeks=2)
return -1 if date < start else 0 if date < end else 1
Test cases:
for i in range(14):
dt = datetime.today().date() + timedelta(days=i)
print(dt, in_next_week(dt))
Related
from datetime import datetime
from datetime import timedelta
#this is the start day
day = input()
#this is number of days input
num=int(input())
#this is the start date of the shipment
temp = input()
#this is the date format the string into a day using the strptime object
start_day = datetime.strptime(day, '%A')
#this line will format the string input into a date
format1 = datetime.strptime(temp, '%d-%m-%Y')
#this line will add number input onto the date
arrival = format1 + timedelta(days=num)
for i in range(num):
a = arrival - timedelta(days=i)
if a.weekday() <5 :
print(a.strftime('%d-%m-%Y'))
The above code gives me three weekday dates but I am expecting four.
This is my output:
05-03-2019
04-03-2019
01-03-2019
but I need this:
01-03-2019
04-03-2019
05-03-2019
06-03-2019
All dates starting with the oldest first e.g. ascending order.
Here is the assignment I have:
Radan Logistics is a mid sized Shipping Company known for its Customer oriented delivery services. The Company Management intended to place an information kiosk in their Head Office which would help their Customers to fetch all the desired information with regards to their shipment. One such vital information that Customers would prefer to know is the details of the working days of the Company which would help them track their shipments.
Help the Management write a program for the kiosk, that when given the start day, number of days 'n' and the start date, will output the dates of the 'n' business days (excluding Saturday and Sunday).
Input Format:
The first line of input is a String, the start day.
The second line of the input is the number of days.
Third line is a string that correponds to the start date of the shipment.
Output Format:
Output is list of dates of n working days separated by new line.
Sample Input 1:
Monday
7
03-12-2007
Sample Output 1:
04-12-2007
05-12-2007
06-12-2007
07-12-2007
10-12-2007
11-12-2007
Sample Input 2:
Thursday
10
25-02-2012
Sample Output 2:
26-02-2012
29-02-2012
01-03-2012
02-03-2012
03-03-2012
04-03-2012
07-03-2012
08-03-2012
09-03-2012
The issue seems to be that you're looping through an ascending range of numbers, but that number is subtracted to get the result. For example 10-1=9, 10-2=8, 10-3=7, etc. You can instead loop through range(num) in descending order. Also, range() by default goes from index zero up to and not including num. To have num included, you may want range(num + 1)
for i in reversed(range(num + 1)):
a = arrival - timedelta(days=i)
if a.weekday() <5 :
print(a.strftime('%d-%m-%Y'))
To show 5 days you have to make a.weekday() <=5 not num+1
and add reversed to range to reverse the showing of data
for i in reversed(range(num)):
a = arrival - timedelta(days=i)
if a.weekday() <=5 :
print(a.strftime('%d-%m-%Y'))
import datetime
start = '01-03-2019'
num_days = 7
date_list = [datetime.datetime.strptime(start, "%d-%m-%Y") + datetime.timedelta(days=x) for x in range(num_days)]
list_of_weekdays = [day.strftime('%d-%m-%Y') for day in date_list if day.isoweekday() in range(1, 6)]
[print(day) for day in list_of_weekdays[::-1]]
Print range of dates in descending order, i.e. from newest to oldest.
from datetime import datetime, timedelta
def range_of_dates_from_interval(start, end, date_format='%d-%m-%Y'):
start_date = datetime.strptime(start, date_format).date()
end_date = datetime.strptime(end, date_format).date()
d = timedelta(days=1)
date = end_date
while date != start_date:
print(date.strftime(date_format))
date -= d
print(date.strftime(date_format))
def range_of_dates_with_step(start, amount_days, date_format='%d-%m-%Y'):
start_date = datetime.strptime(start, date_format).date()
d = timedelta(days=1)
for i in range(amount_days-1, -1, -1):
print((start_date + d*i).strftime(date_format))
date_format = '%d-%m-%Y'
# test first function
start = '29-03-2019'
end = '02-04-2019'
range_of_dates_from_interval(start, end, date_format=date_format)
#02-04-2019
#01-04-2019
#31-03-2019
#30-03-2019
#29-03-2019
# test second function
start = '29-03-2019'
amount_days = 5
range_of_dates_with_step(start, amount_days, date_format=date_format)
#02-04-2019
#01-04-2019
#31-03-2019
#30-03-2019
#29-03-2019
EDIT: answer of the assignment
import datetime
# not needed but useful for display information
def weekdays_iso(day_num_format=True) -> dict:
out = {}
d0 = datetime.date.fromordinal(1) # day zero
d, a_day = d0, datetime.timedelta(days=1)
for i in range(7):
if day_num_format:
out[d.strftime("%A")] = i+1
else:
out[i+1] = d.strftime("%A")
d += a_day
return out
# main function
def get_business_days(num_b_days, start, date_format='%d-%m-%Y') -> list:
b_days = []
start_date = datetime.datetime.strptime(start, date_format).date()
b_day, a_day = start_date, datetime.timedelta(days=1)
while num_b_days > 1:
b_day += a_day
if b_day.isoweekday() not in {6, 7}:
b_days.append(b_day)
num_b_days -= 1
return b_days
WEEKDAYS_ISO = weekdays_iso(day_num_format=False)
date_format = '%d-%m-%Y'
Test 1
start = "03-12-2007"
n_b_days = 7
# result
b_days = get_business_days(n_b_days, start, date_format=date_format)
# check
for d in b_days:
print(d.strftime(date_format), WEEKDAYS_ISO[d.isoweekday()])
Output 1:
04-12-2007 Tuesday
05-12-2007 Wednesday
06-12-2007 Thursday
07-12-2007 Friday
10-12-2007 Monday
11-12-2007 Tuesday
Test 2
start = "25-02-2012"
n_b_days = 10
# result
b_days = get_business_days(n_b_days, start, date_format=date_format)
# check
for d in b_days:
print(d.strftime(date_format), WEEKDAYS_ISO[d.isoweekday()])
Output 2:
27-02-2012 Monday
28-02-2012 Tuesday
29-02-2012 Wednesday
01-03-2012 Thursday
02-03-2012 Friday
05-03-2012 Monday
06-03-2012 Tuesday
07-03-2012 Wednesday
08-03-2012 Thursday
I want tot create a list of dates starting from 10/09/2020 with increments of 182 days until reaching 05/03/2020.
my code is this :
start_date="10/09/2020"
last_date="05/03/2020"
start_date=datetimedatetime.strptime(date,"%d/%m/%Y").date()
last_date=datetimedatetime.strptime(date,"%d/%m/%Y").date()
dates=[]
while dates[-1] != last_date:
i=star_date+timedelta(days=182)
dates.append(i)
dates[i]=i+timedelta(days=pago_cupon)
I don't know what's your problem.
You can try this code
from datetime import date, timedelta
start_day = date(year=2020, month=9, day=10)
end_day = date(year=2021, month=3, day=5)
one_data_delta = timedelta(days=1)
res = []
while end_day != start_day:
start_day += one_data_delta
res.append(start_day)
print(res)
A few problems:
You had a spelling mistake in your for loop star_date instead of start_date.
Also, you may want to change the comparison from != to less than equals or more than equals.
I am checking against (last_date - timedelta(days=182)) so that we won't exceed the last_date.
Your original start date is after your original end date.
As an example, I have adjusted the end day to be a couple years in the future.
I'm appending the dates as text.
from datetime import datetime, timedelta
start="10/09/2020"
last="05/03/2022"
start_date=datetime.strptime(start,"%d/%m/%Y")
last_date=datetime.strptime(last,"%d/%m/%Y")
dates=[]
while start_date <= (last_date - timedelta(days=182)):
start_date += timedelta(days=182)
dates.append(start_date.strftime("%d/%m/%Y"))
# not quite sure what you are trying to do here:
#dates[i]=i+timedelta(days=pago_cupon)
print(dates)
Output:
['11/03/2021', '09/09/2021']
I'm trying to check if first date of the month and the last date of the month lies in a range of dates (the range is 7 days window starting from current date) . below is an example for what I'm trying to achieve:
import datetime, calendar
today = datetime.date.today()
date_list = [today + datetime.timedelta(days=x) for x in range(0, 7)]
lastDayOfMonth = today.replace(day=calendar.monthrange(today.year,today.month)[-1])
if 1 in [ date_list[i].day for i in range(0, len(date_list))]:
print "we have first day of month in range"
elif lastDayOfMonth in [ date_list[i].day for i in range(0, len(date_list))]:
print " we have last date of month in the range"
I'm wondering if there is a cleaner way for doing that? I also want to print the exact date if I find it in the list but I don't know how without expanding the for loop in the if statement and save print date_list[i] if it matches my condition. so instead of printing the message when I find the first day in the range I should print the actual date. same for last date.
Thanks in advance!
The only thing I can come up with, without having to make use of iteration is:
import datetime, calendar
today = datetime.date.today()
week_from_today = today + datetime.timedelta(days=6)
last_day_of_month = today.replace(day=calendar.monthrange(today.year,today.month)[-1])
if today.month != week_from_today.month:
print datetime.date(week_from_today.year, week_from_today.month, 1)
elif today <= last_day_of_month <= week_from_today:
print last_day_of_month
since today it's 2016-06-02 it's hard to test the code.
Try changing the variable today to another day. I used the dates 2016-05-25 and 2016-05-26 to test the code.
to set a custom date: today = datetime.date(yyyy, m, d)
Please tell me how I can list next 24 months' start dates with python,
such as:
01May2014
01June2014
.
.
.
01Aug2015
and so on
I tried:
import datetime
this_month_start = datetime.datetime.now().replace(day=1)
for i in xrange(24):
print (this_month_start + i*datetime.timedelta(40)).replace(day=1)
But it skips some months.
Just increment the month value; I used datetime.date() types here as that's more than enough:
current = datetime.date.today().replace(day=1)
for i in xrange(24):
new_month = current.month % 12 + 1
new_year = current.year + current.month // 12
current = current.replace(month=new_month, year=new_year)
print current
The new month calculation picks the next month based on the last calculated month, and the year is incremented every time the previous month reached December.
By manipulating a current object, you simplify the calculations; you can do it with i as an offset as well, but the calculation gets a little more complicated.
It'll work with datetime.datetime() too.
To simplify arithmetics, try/except could be used:
from datetime import date
current = date.today().replace(day=1)
for _ in range(24):
try:
current = current.replace(month=current.month + 1)
except ValueError: # new year
current = current.replace(month=1, year=current.year + 1)
print(current.strftime('%d%b%Y'))
I have a function that removes a file after a certain amount of time. The problem is that it works at later parts of the month, but when I try and remove 7 days from the start of the month it will not substract into the previous month. Does anyone know how to get this to work? The code is below that works out the date and removes the days.
today = datetime.date.today() # Today's date Binary
todaystr = datetime.date.today().isoformat() # Todays date as a string
minus_seven = today.replace(day=today.day-7).isoformat() # Removes 7 days
Thanks for any help.
minus_seven = today - datetime.timedelta(days = 7)
The reason this breaks is that today is a datetime.date; and as the docs say, that means that today.day is:
Between 1 and the number of days in the given month of the given year.
You can see why this works later in the month; but for the first few days of the month you end up with a negative value.
The docs immediately go on to document the correct way to do what you're trying to do:
date2 = date1 - timedelta Computes date2 such that date2 + timedelta == date1.