I need some help with my code. I have a trouble with changing the strings.
I am checking with the strings if the variable getTime3 have a string 30 then I want to replace it with 00. On my code, it will find the string 30 to replace it with 0030 which is wrong. It should be 00.
Here is the code:
if getTime3 == '11:30PM':
self.getControl(346).setLabel('12:00AM')
elif getTime3 == '12:30PM':
self.getControl(346).setLabel('1:00AM')
else:
ind = getTime3.find(':')
if getTime3[ind+1:ind+3]=='30':
getTime3 = getTime3[:ind]+':00'+getTime3[+2:]
self.getControl(346).setLabel(getTime3)
else:
getTime3 = str(int(getTime3[:ind])+1)+':30'+getTime3[+2:]
self.getControl(346).setLabel(getTime3)
What I am expect for the two special cases, when the program finds the :, it will check if 30 is present then change the current hour to the next hour and make a new string with AM/PM label, example: change from 8 to 9 and replace 30 with 00 to make it to show 9:00PM. If the ending is 00 then I want to change 00 to 30 instead. I want to add 30 in the minute section and again preserves the AM/PM part. If the getTime3 have the string 11:30AM then I want to change it to 12:00PM.
Can you please help me with how to fix the 0030 to make it to show 00 instead and add the next hour?
With Python, slice like x[a:b] in the slice starting at a (inclusive), and finishing at b (exclusive).
So: getTime3[:ind] is the slice from 0 to ind exclusive, which is the hours without the ":".
And indexes are absolute index, not relative. So getTime3[+2:] is the same as getTime3[2:], which correspond to the substring starting at index 2.
What you want is:
getTime3 = getTime3[:ind] + ':00' + getTime3[ind + 3:]
# or
getTime3 = getTime3[:ind + 1] + '00' + getTime3[ind + 3:]
Example:
getTime3 = '08:30PM'
ind = getTime3.index(":")
getTime3[:ind] + ':00' + getTime3[ind + 3:]
# -> '08:00PM'
EDIT
If you want to do some calculation on time, you can use the datetime module.
time_fmt = '%I:%M%p'
Is the format used to represent time like '09:30PM', where:
%I Hour (12-hour clock) as a zero-padded decimal number.
%M Minute as a zero-padded decimal number.
%p Locale’s equivalent of either AM or PM.
How to add 30 min:
import datetime
time3 = '09:30PM'
dt3 = datetime.datetime.strptime(time3, time_fmt)
dt3 += datetime.timedelta(minutes=30)
time3 = dt3.strftime(time_fmt)
If you want to set the minutes to 0, you can do:
dt3 = datetime.datetime.strptime(time3, time_fmt)
dt3 = d3.replace(minute=0)
Please don't use the wrong tool for the task. You are manipulating times, yet using strings to do it. Start with this to turn 11:30PM into 12:00AM:
import datetime
t3 = datetime.datetime.strptime(getTime3, '%I:%M%p')
t3 += datetime.timedelta(minutes=30)
print(t3.strftime('%I:%M%p'))
Adding timedelta(minutes=30) makes the intent perfectly clear. Some relevant documentation is at https://docs.python.org/3/library/datetime.html#strftime-and-strptime-behavior
Related
I have exported some data from another programm, where I added up time for a station waiting.
So after some time, I have the format '32:00:00:33.7317' for the waiting time.
This is my function to convert every date into the format I want:
def Datum_formatieren(Datensatz):
if len(str(Datensatz)) == 24:
return datetime.datetime.strptime(Datensatz, "%d.%m.%Y %H:%M:%S.%f").strftime("%d%H%M")
elif len(str(Datensatz)) == 3:
return 0
#return datetime.datetime.strptime(Datensatz, "%S.%f").strftime("%d%H%M")
elif len(str(Datensatz)) == 5:
return str(Datensatz)
elif len(str(Datensatz)) == 7:
return str(Datensatz)
elif len(str(Datensatz)) == 6:
return datetime.datetime.strptime(str(Datensatz), "%S.%f").strftime("%d%H%M")
elif len(str(Datensatz)) == 9 or len(str(Datensatz))==10:
return datetime.datetime.strptime(str(Datensatz), "%M:%S.%f").strftime("%d%H%M")
elif len(str(Datensatz)) == 12 or len(str(Datensatz)) ==13:
return datetime.datetime.strptime(str(Datensatz), "%H:%M:%S.%f").strftime("%d%H%M")
elif len(str(Datensatz)) == 15 or len(str(Datensatz)) == 16:
return datetime.datetime.strptime(str(Datensatz), "%d:%H:%M:%S.%f").strftime("%d%H%M")
I get the following error since python does not recognize days above 30 or 31:
ValueError: time data '32:00:00:33.7317' does not match format '%d:%H:%M:%S.%f'
How do I convert all entries with days above 31 into a format, which python can recognize?
You cannot use datetime.datetime.strptime() to construct datetimes that are invalid - why see other answer.
You can however leverage datetime.timespan:
import datetime
def Datum_formatieren(Datensatz):
# other cases omitted for brevity
# Input: "days:hours:minutes:seconds.ms"
if len(Datensatz) in (15,16):
k = list(map(float,Datensatz.split(":")))
secs = k[0]*60*60*24 + k[1]*60*60 + k[2]*60 + k[3]
td = datetime.timedelta(seconds=secs)
days = td.total_seconds() / 24 / 60 // 60
hours = (td.total_seconds() - days * 24*60*60) / 60 // 60
minuts = (td.total_seconds() - days *24*60*60 - hours * 60*60) // 60
print(td)
return f"{td.days}{int(hours):02d}{int(minuts):02d}"
print(Datum_formatieren("32:32:74:33.731"))
Output for "32:32:74:33.731":
33 days, 9:14:33.731000 # timespan
330914 # manually parsed
You are misusing datetime wich only map to correct dates with times - not "any amount time passed".
Use a timedelta instead:
Adapted from datetime.timedelta:
from datetime import datetime, timedelta
delta = timedelta( days=50, seconds=27, microseconds=10,
milliseconds=29000, minutes=5, hours=8, weeks=2 )
print(datetime.now() + delta)
You can add any timedelta to a normal datetime and get the resulting value.
If you want to stick wich your approach you may want to shorten it:
if len(str(Datensatz)) == 9 or len(str(Datensatz))==10:
if len(Datensatz) in (9,10):
Related: How to construct a timedelta object from a simple string (look at its answers and take inspiration with attribution from it)
You're taking the Datensatz variable, converting it to string using str(), then parsing it back into an internal representation; there is almost always a better way to do it.
Can you check what type the Datensatz variable has, perhaps print(type(Datensatz)) or based on the rest of your code?
Most likely the Datensatz variable already has fields for the number of days, hours, minutes and seconds. It's usually much better to base your logic on those directly, rather than converting to string and back.
As others have pointed out, you're trying to use a datetime.datetime to represent a time interval; this is incorrect. Instead, you need to either:
Use the datetime.timedelta type, which is designed for time intervals. It can handle periods over 30 days correctly:
>>> print(datetime.timedelta(days=32, seconds=12345))
32 days, 3:25:45
>>>
Since your function is named Datum_formatieren, perhaps you intend to take Datensatz and convert it to string, for output to the user or to another system.
In that case, you should take the fields directly in Datensatz and convert them appropriately, perhaps using f-strings or % formatting. Depending on the situation, you may need to do some arithmetic. The details will depend on the type of Datensatz and the format you need on the output.
I have a path files which are named by time (201803061500) etc. What I need is a time conversion, because I use while loop to open a few of them there is an error when I want files from for example (...1555 to ... 1615) and Python sees an obivous problem because after 1555 is 1560, but I want him to convert that to time so after (...1555 will be ... 1600) any ideas how to use it?
Btw. Time conversion must be contain 4 digits, so it cannot be 16:00/16-00 etc. it must be 1600, because it goes as an input to my pathfile. Any ideas?
UPDATE - I did this, but this code is rubbish and I think my problem might be solved by one command.
Start_time_hours = input('Enter start time (hh): ' )
Start_time_minutes = input('Enter start time (mm): ')
if Start_time_hours >= 24:
print ("Values from 00 to 23 only!")
if Start_time_minutes >= 60:
x = Start_time_hours + 1
y = Start_time_minutes - Start_time_minutes
if y == 0:
print "Ok"
print x, y
if Start_time_minutes <= 55:
print Start_time_hours, Start_time_minutes
One easy way to handle unformated time is the datetime. You can first strip your strings and then do whatever you want !
from datetime import datetime, timedelta
from time import strtime
datetime_object = datetime.strptime(file_name, '%Y%m%d%H%M')
print(datetime_object) # returns '2018-03-06 15:00:00'
delta = timedelta(minutes=5)
next_time = datetime_object + delta
print(next_time) # returns '2018-03-06 15:05:00'
Finally you can get your string back by using time.strftime() function
new_string = next_time.strftime('%Y%m%d%H%M')
print(new_string) # returns '201803061505'
Source datetime: https://docs.python.org/3/library/datetime.html#strftime-and-strptime-behavior
Source time: https://docs.python.org/2/library/time.html
Start_time_hours += (Start_time_minutes / 60)
Start_time_minutes %= 60
Start_time_minutes += 5
Those three lines solved my problem, datetime also works, but if you put those variables to input pathfile, you'll get an error. That's why I've choosen this solution.
I need to make a simple program which converts a 24 hour time which is input, into 12 hour time, which produces an error if an incorrect time is put in. I currently have the code below, however, I have a few issues. One issue is that if "0924" is input, it outputs "924 am", when I need it to produce "9:24am" (the space isn't hugely important but it's preferred). Also, I'm not entirely sure where to start for doing 0001-0059, because "0001" for example produces "1 am", which is obviously incorrect.
print("Enter a time in 24 hour time, e.g. '1620'")
time = (int(input("Time: ")))
normal = 0
if (time == 0000):
normal="12:00am"
print (normal)
elif (time>1200):
normal = (time - 1200)
print (int(normal), ("pm"))
elif (time<1200):
normal = time
print (int(normal), ("am"))
Thanks in advance for any help!
Try this
import time
timevalue_24hour = "1620";
timevalue_24hour = timevalue_24hour[:2] + ':' + timevalue_24hour[2:]
print (timevalue_24hour)
t = time.strptime(timevalue_24hour, "%H:%M")
timevalue_12hour = time.strftime( "%I:%M %p", t )
print (timevalue_12hour)
Take input as a string. Assign it to timevalue_24hour and rest will work
When printing, normal is just a number. The 0s disappear because you don't write 0s in front of numbers normally. I would suggest doing something like this
def normal_check(num):
if num < 10:
return "000"+str(num)
elif num < 100:
return "00"+str(num)
elif num < 1000:
return "0"+str(num)
else:
return str(num)
print("Enter a time in 24 hour time, e.g. '1620'")
time = (int(input("Time: ")))
normal = 0
if (time == 0000):
normal="12:00am"
print (normal)
elif (time>1200):
normal = normal_check(time - 1200)
print (normal, ("pm"))
elif (time<1200):
normal = normal_check(time)
print (normal, ("am"))
The best way to do this will be to take the input as an str rather than int. Take it in as str and split it into two int values of two digits.
Then the first string if less than 12 will be hour else subtract 12 from first str and use PM. Also, the second str will just be minutes.
Without using any libraries, I'm trying to solve the Hackerrank problem "Time Conversion", the problem statement of which is copied below.
I came up with the following:
time = raw_input().strip()
meridian = time[-2:] # "AM" or "PM"
time_without_meridian = time[:-2]
hour = int(time[:2])
if meridian == "AM":
hour = (hour+1) % 12 - 1
print ("%02d" % hour) + time_without_meridian[2:]
elif meridian == "PM":
hour += 12
print str(hour) + time_without_meridian[2:]
However, this fails on one test case:
Since the test cases are hidden to the user, however, I'm struggling to see where the problem is occurring. "12:00:00AM" is correctly converted to "00:00:00", and "01:00:00AM" to "01:00:00" (with the padded zero). What could be wrong with this implementation?
It's even simpler than how you have it.
hour = int(time[:2])
meridian = time[8:]
# Special-case '12AM' -> 0, '12PM' -> 12 (not 24)
if (hour == 12):
hour = 0
if (meridian == 'PM'):
hour += 12
print("%02d" % hour + time[2:8])
You've already solved the problem but here's another possible answer:
from datetime import datetime
def solution(time):
return datetime.strptime(time, '%I:%M:%S%p').strftime('%H:%M:%S')
if __name__ == '__main__':
tests = [
"12:00:00PM",
"12:00:00AM",
"07:05:45PM"
]
for t in tests:
print solution(t)
Although it'd be using a python library :-)
from datetime import datetime
#Note the leading zero in 05 below, which is required for the formats used below
regular_time = input("Enter a regular time in 05:48 PM format: ")
#%I is for regular time. %H is for 24 hr time, aka "military time"
#%p is for AM/PM
military_time = datetime.strptime(regtime, '%I:%M %p').strftime('%H:%M')
print(f"regular time is: {regular_time"}
print(f"militarytime is {military_time}")
The following link proved to be very helpful: https://strftime.org/
I figured it out: it was converting "12:00:00PM" to "24:00:00" and not "12:00:00". I modified the code as follows:
time = raw_input().strip()
meridian = time[-2:] # "AM" or "PM"
time_without_meridian = time[:-2]
hour = int(time[:2])
if meridian == "AM":
hour = (hour+1) % 12 - 1
print ("%02d" % hour) + time_without_meridian[2:]
elif meridian == "PM":
hour = hour % 12 + 12
print str(hour) + time_without_meridian[2:]
leading to it passing all the test cases (see below).
dt_m = datetime.datetime.fromtimestamp(m_time)
hour_m = (dt_m.hour%12)+1 #dt_m.hour+1
offset_dt = datetime.datetime(dt_m.year, dt_m.month, dt_m.day, hour_m , dt_m.minute, dt_m.second, dt_m.microsecond)
In the code shown below, I need to manipulate the time var in python to display a date/time stamp in python to represent that delay.
For example, when the user enters the delay time in hours, I need to set the jcarddeliver var to update itself with the value of the current date/time + delay.
Also it should update the date var as well. For example, if the date is 24 Feb and time is 15:00 hrs and the delay time is 10 hrs, the jcarddeliver date should change to 25 Feb.
jcarddate = time.strftime("%a %m/%d/%y", time.localtime())
jcardtime = time.strftime("%H:%M:%S", time.localtime())
delay = raw_input("enter the delay: ")
jcarddeliver = ??
I just hope I am making sense.
You could try the datetime module, e.g.
import datetime
now = datetime.datetime.now()
delay = float (raw_input ("enter delay (s): "))
dt = datetime.timedelta (seconds=delay)
then = now + dt
print now
print then
The result of time.time() is a floating point value of the number of seconds since the Epoch. You can add seconds to this value and use time.localtime(), time.ctime() and other functions to get the result in various forms:
>>> now = time.time()
>>> time.ctime(now)
'Fri Sep 04 16:19:59 2009' # <-- this is local time
>>> then = now + (10.0 * 60.0 * 60.0) # <-- 10 hours in seconds
>>> time.ctime(then)
'Sat Sep 05 02:19:59 2009'
" i need to set the jcarddeliver var to update itself with the value of the current date/time + delay"
How about reformulating this to
jcarddeliver should be the current date-time plus the delay.
The "update itself" isn't perfectly sensible.
Try the following:
Try the most obvious way of computing "current date-time plus the delay"
print the result.
Try using localtime() on this result. What do you get?
Try this:
now = time.time()
then = now + 365*24*3600
print time.strftime('%Y-%m-%d', time.localtime(then))