Related
I am trying to get get the time delta i minutes from two different time values.
time1 = 2020-11-28T10:31:12Z
time2 = 2020-11-28T09:10:23.203+0000
Then i will make i condition: if time difference is bigger then x minutes, run code...
Anyone have a solution for that.
I have tried using datetime.datetime.strptime() but cant get them on same format.
Thanks
Using date parser to let it figure out the date format
Code
from dateutil.parser import parse
def time_difference(time1, time2):
# Parse strings into datetime objects
dt1 = parse(time1)
dt2 = parse(time2)
# Get timedelta object
c = dt1 - dt2
# Difference in minutes
return (c.total_seconds()/60)
Test
time1 = "2020-11-28T10:31:12Z"
time2 = "2020-11-28T09:10:23.203+0000"
print(time_difference(time1, time2))
# Output: 80.81328333333333
well assuming you don't need split seconds you could do something like that:
time1 = '2020-11-28T10:31:12Z'
time2 = '2020-11-28T09:10:23.203+0000'
import time
import datetime
def get_timestamp(time_str):
time_splited = time_str.split('T')
time_str_formatted = ' '.join([time_splited[0],time_splited[1][:8]])
return time.mktime(datetime.datetime.strptime(time_str_formatted,"%Y-%m-%d %H:%M:%S").timetuple())
print(get_timestamp(time1))
print(get_timestamp(time2))
reformatting both times to the same time format.
then your condition would look like:
if abs(get_timestamp(time1) -get_timestamp(time2) ) > x*60:
do_something(....)
The times are not uniform so you will have to make them the same to use strptime. For accuracy I prefer to convert to seconds then you can also at a later stage compare seconds, minutes or hours if you needed to.
import datetime
time1 = '2020-11-28T10:31:12Z'
time2 = '2020-11-28T09:10:23.203+0000'
def minutes_diff():
#Make the times uniform so you can then use strptime
date_time1 = datetime.datetime.strptime(time1[:-1], "%Y-%m-%dT%H:%M:%S")
date_time2 = datetime.datetime.strptime(time2[:-9], "%Y-%m-%dT%H:%M:%S")
#Convert to seconds for accuracy
a_timedelta = date_time1 - datetime.datetime(1900, 1, 1)
b_timedelta = date_time2 - datetime.datetime(1900, 1, 1)
seconds_time_a = a_timedelta.total_seconds()
seconds_time_b = b_timedelta.total_seconds()
#Take one from each other for minutes
time_in_minutes = (seconds_time_a - seconds_time_b) / 60
#Then decide what to do with it
if time_in_minutes < 60: # 1 hour
print('Less than an hours do something')
else:
print('More than an hour do nothing')
minutes_diff()
DARRYL, JOHNNY and MARCIN, thanks for your solutions, problem solved!!
Andy
I have a time from five minutes ago, using datetime.time.now() and I need to know what the time would be if I subtracted that time from the current time.
Try 1 - Didn't Work:
from datetime import datetime, timedelta
time1 = datetime.now()
time2 = datetime.now() + timedelta(minutes=5)
print(time1 - time2)
This gave me "-1 day, 23:54:59.999987".
Try 2 - Worked, but is there a better way?:
time1 = datetime.now()
time2 = datetime.now() + timedelta(minutes=5)
print(str(time1 - time2).split(',')[1])
This gave me the desired result, but is there a method besides string manipulation?
You wanted to take an advice how to use a time object?
Well, if you want to specify a format of string representation of your time, just use strftime
Example below:
from datetime import datetime, timedelta
time1 = datetime.now()
time2 = datetime.now() + timedelta(minutes=5)
print((time1 - time2).strftime('%H:%M:%S'))
Assuming you want the time 5 minutes ago, you can use timedelta without any string manipulation:
five_min_ago = datetime.datetime.now() - datetime.timedelta(minutes = 5)
I am taking time as input from the user in the HH:MM format. Let's say 00:00 and now I want to keep adding a minute to the time and make it 00:01, 00:02 and so on.
Also, I am taking two inputs form the user start_time and end_time as strings. How can I calculate the difference between the two times as well in minutes?
I am new to Python and any help would be appreciated!
I am using the below code:
#to calculate difference in time
time_diff = datetime.strptime(end_time, '%H:%M') - datetime.strptime(start_time, '%H:%M')
minutes = int(time_diff.total_seconds()/60)
print minutes
#to convert string to time format HH:MM
start_time = datetime.strptime(start_time, '%H:%M').time()
#to increment time by 1 minute
start_time = start_time + datetime.timedelta(minutes=1)
I am not able to increment the start_time using timedelta.
import datetime
time_diff = datetime.datetime.strptime(end_time, '%H:%M') - datetime.datetime.strptime(start_time, '%H:%M')
minutes = int(time_diff.total_seconds()/60)
print minutes
datetime is a class of the datetime module that has a classmethod called strptime. The nomenclature is a bit confusing, but this should work as you intend it to.
As for adding a time delta, you'll need store the start time as a datetime object in order to get that to work:
start_datetime = datetime.datetime.strptime(start_time, '%H:%M')
start_datetime = start_datetime + datetime.timedelta(minutes=1)
print start_datetime
First part of your question, you can use the datetime module:
from datetime import datetime as dt
from datetime import timedelta as td
UsrInput = '00:00'
fmtString = '%H:%M'
myTime = dt.strptime(UsrInput, fmtString)
increment = td(0,1)
for count in range(10):
myTime += increment
print (dt.strftime(myTime, fmtString))
Second part will also use datetime, as such:
from datetime import datetime as dt
from datetime import timedelta as td
start_time = '00:01'
end_time = '00:23'
fmtString = '%H:%M'
myStart = dt.strptime(start_time, fmtString)
myEnd = dt.strptime(end_time, fmtString)
difference = myEnd - myStart
print(td.strftime(difference, '%M')
I am running into following error while calculating time diff?how to fix it?
from datetime import datetime, date
import time
print "Start : %s" % time.ctime()
start_time = time.ctime()
#do something
print "How to calculate time diff?"
end_time = time.ctime()
total_elapsed_time = datetime.combine(date.today(), end_time) - datetime.combine(date.today(), start_time)
print "TOTAL ELAPSED TIME" + str(total_elapsed_time)
Error:-
Traceback (most recent call last):
File "time_diff.py", line 8, in <module>
total_elapsed_time = datetime.combine(date.today(), end_time) - datetime.combine(date.today(), start_time)
TypeError: combine() argument 2 must be datetime.time, not str
The error clearly states that argument 2 of combine() must be datetime.time.
You should have an instance of datetime.time which is something like:
d = datetime.now()
timepart = d.time()
datepart = d.date()
datetime.combine(datepart, timepart)
First of all you are mixin 3 data types, so your approach is fundamentally wrong.
There are two (basic) ways, how to get and store time in python (two from std lib):
timestamp - you import time module, then time.time() will return a float - a number of seconds from epoch, then any comparison is just like comparing float numbers, if number is greater - then time that it represents is in the future, any difference between dates is a number too - representing number of seconds between dates - so it is as well simple to convert it minutes, hours etc. by dividing by 60, 3600 etc.
datetime object you import datetime.datetime to get an object which you can operate on, it is much simpler to operate on than timestamp, because it is automatically converted to human readable format, all comparison operators works and any difference between dates (date2-date1) is returned as datetime.timedelta where you can extract number of days, seconds and milliseconds it represents.
so in your code you can use:
timestamps:
import time
date1 = time.time()
print 'Start time: %s' % time.ctime(date1)
...
date2 = time.time()
print 'End time: %s' % time.ctime(date2)
print 'Time it took: %0.2f seconds' % (date2 - date1)
datetime
from datetime import datetime
date1 = datetime.now()
print 'Start time: %s' % date1
...
date2 = datetime.now()
print 'End time: %s' % date2
print 'Time it took: %s' % (date2 - date1)
from datetime import datetime, timedelta
def calc():
s = datetime.now()
e = datetime(day=21, month=7, year=2016, hour=12, minute=0)
diff = e - s
diff is datetime.timedelta instance now. On this instance you have properties such as days, seconds, microseconds and function by name total_seconds.
PS: This is for reference only. I hope it helps to achieve a solution
time.ctime() returns a string, that is the source of your error.
See Python time.ctime
time.time() is probably what you are looking for:
See Python ticks
Your start_time and end_time are strings. Also your datetime.combine should have the 2nd argument as a datetime.time object. Your time.ctime returns the date and year information as well. So first extract only the time information and then convert it to a datetime.time object.
You can store the start and end time both using ctime and then do something like this:
import datetime
import time
#store at start time
a=datetime.datetime.strptime(time.ctime(), "%a %b %d %H:%M:%S %Y")
#store at end time
b=datetime.datetime.strptime(time.ctime(), "%a %b %d %H:%M:%S %Y")
print b-a
As #Jerzyk pointed out, there is no need to parse it unless you want to display it in a particular format. So alternatively, you could do:
a=datetime.datetime.now()
b=datetime.datetime.now()
print b-a
This will return a datetime.timedelta that you can parse in order to display the result in the way you want.
I have data in a file with dates marked, for example, '2015.05.05-11:46', and want to read these lines and then see if they fulfill certain conditions. For example, as input to the function, I may have
get_times('hour', -3.0, -1.2)
which has function defintion:
get_times(unit, start_time, end_time):
which means I want to return all strings that are from -3.0 hours in the past to -1.2 hours in the past. I can get the current time with now = datetime.datetime.now(). Assuming I read in time1 = '2015.05.05-11:46', how do I compare that to now and find out if it is within start_time and end_time units from now?
You can use < and > operators normally.
But for that to work, you have to make all data be datetime type.
For instance:
time_str = "2015.05.05-11:46"
reference_time = datetime.datetime.strptime(time_str, "%Y.%m.%d-%H:%M")
start_time = reference_time - datetime.timedelta(hours=3)
end_time = reference_time - datetime.timedelta(hours=1.2)
now = datetime.datetime.now()
if end_time <= now <= start_time:
print 'It is in between'
You can also pass arguments to timedelta function using a dictionary:
>>> a = datetime.timedelta(hours=3, minutes=10)
>>> args = {'hours': 3, 'minutes': 10}
>>> b = datetime.timedelta(**args)
>>> a == b
True
Use datetime.strptime to convert your string '2015.05.05-11:46'
then = datetime.datetime.strptime('2015.05.05-11:46', "%Y.%m.%d-%H:%M")
now = datetime.datetime.now()
Then use datetime.timedelta to compare times.
tdelta = now - then
if datetime.timedelta(hours=1.2) < tdelta < datetime.timedelta(hours=3.0):
print "In range"
For writing your function, you'll probably want to stick to the units that are in datetime.timedelta, unless you have a good reason not to.
class datetime.timedelta([days[, seconds[, microseconds[, milliseconds[, minutes[, hours[, weeks]]]]]]])
So, 'days', 'seconds', 'microseconds', 'milliseconds', 'minutes', 'hours', 'weeks'
A couple things need to be done in your situation. First, you need to convert your datetime strings to datetime objects for easy comparison. We do this via strptime:
input_datetime = datetime.datetime.strptime(i, '%Y.%m.%d-%H:%M')
We also need the function to return start and end times based on your input. If you can make a slight modification and utilize hours instead of hour, we can do this without setting up a large if/elif block.
def get_times(unit, start_time, end_time):
now = datetime.datetime.now()
start_kwarg = {unit: start_time}
end_kwarg = {unit: end_time}
time_start = now + datetime.timedelta(**start_kwarg)
time_end = now + datetime.timedelta(**end_kwarg)
return time_start, time_end
This takes your unit and creates a dictionary that is passed as a keyword argument to timedelta. Since hours is one of the arguments it accepts, we can utilize the keyword instead of mapping hour to hours. Then we return start and end time.
Finally, we just need to compare that the input time is between start and end:
start < input_datetime < end
A final script could look like this:
import datetime
def get_times(unit, start_time, end_time):
now = datetime.datetime.now()
start_kwarg = {unit: start_time}
end_kwarg = {unit: end_time}
time_start = now + datetime.timedelta(**start_kwarg)
time_end = now + datetime.timedelta(**end_kwarg)
return time_start, time_end
start, end = get_times('hours', -3.0, -1.2)
input_times = [
'2015.05.12-11:46',
'2014.05.12-11:46',
'2016.05.12-11:46',
'2015.04.12-11:46',
'2015.05.05-11:46'
]
for i in input_times:
input_datetime = datetime.datetime.strptime(i, '%Y.%m.%d-%H:%M')
print "{} => {}".format(input_datetime, start < input_datetime < end)
Output would look like this (if run at 12:46pm on 2015-05-12):
2015-05-12 11:46:00 => True
2014-05-12 11:46:00 => False
2016-05-12 11:46:00 => False
2015-04-12 11:46:00 => False
2015-05-05 11:46:00 => False
hope this is what you are looking for:
import datetime
import time
def get_times(unit, start_time, end_time):
now = datetime.datetime.now().timetuple()
matched_dates = []
for date in your_file:
converted_date = time.strptime(date,"%Y.%m.%d-%H:%M")
if converted_date.tm_hour > (now.tm_hour + start_time) and converted_date.tm_hour < (now.tm_hour + end_time):
matched_dates.append(date)
return matched_dates
To compare time from the file, you should convert it to UTC time (POSIX timestamp) or an aware datetime object (local time + utc offset).
start_time, end_time = get_times('hour', -3, -1.2)
if start_time <= utc_time < end_time:
# utc_time is in between
You should not use start_time <= naive_local_time < end_time. Convert input time to UTC or create an aware datetime objects instead.
If local times in your input file are consecutive then you could use that fact to disambiguate the timestamps if necessary, see Parsing of Ordered Timestamps in Local Time (to UTC) While Observing Daylight Saving Time.
More explanation and solutions that use time.mktime(), pytz, aware datetime objects are in: Find if 24 hrs have passed between datetimes - Python.
Why you should not use datetime.now()
datetime.now() returns local time as a naive datetime object may be ambiguous e.g., during a DST transition:
>>> from datetime import datetime
>>> import pytz
>>> tz = pytz.timezone('America/New_York')
>>> tz.localize(datetime(2015,11,1,1,30), is_dst=None)
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "/usr/lib/python2.7/dist-packages/pytz/tzinfo.py", line 349, in localize
raise AmbiguousTimeError(dt)
pytz.exceptions.AmbiguousTimeError: 2015-11-01 01:30:00
>>> tz.localize(datetime(2015,11,1,1,30), is_dst=True).astimezone(pytz.utc)
datetime.datetime(2015, 11, 1, 5, 30, tzinfo=<UTC>)
>>> tz.localize(datetime(2015,11,1,1,30), is_dst=False).astimezone(pytz.utc)
datetime.datetime(2015, 11, 1, 6, 30, tzinfo=<UTC>)
Note: if you remove UTC offset then the same local time may correspond to different UTC time. datetime.utcnow() is unambiguous (except perhaps during a leap second such as 2015-06-30T23:59:60Z).
How to implement get_times('hour', -3.0, -1.2)
Use UTC time or aware datetime objects:
#!/usr/bin/env python
from datetime import datetime, timedelta
def get_times(unit, relative_start, relative_end):
relative_start, relative_end = [timedelta(**{unit+'s': v})
for v in [relative_start, relative_end]]
now = datetime.utcnow() # or datetime.now(timezone.utc).astimezone()
return now + relative_start, now + relative_end