I've been trying to write a script that would accept a text as a timestamp from the user, convert it to a total number of seconds, and then start a timer. For example
Time: 1h:1m:30s
>> 3690s
I've come up with this solution for taking the timestamp from the user
def toSecond(timestring):
t = 0
remove_space = lambda str: str.replace(" ", "")
timestring = remove_space(timestring)
try:
if (":") in timestring:
time = timestring.split(":")
try:
for i in time:
if i[-1] in ("s", "S" "M", "m", "h", "H") and i[0].isnumeric():
if i[-1] in ("h", "H"):
t = int(i[:-1]) * 3600
elif i[-1] in ("m", "M"):
t = int(i[:-1]) * 60
else:
t = int(i[:-1])
else:
print("No num or no char Provided")
except IndexError:
print("nothing provided")
else:
if (
timestring[-1] in ("s", "S" "M", "m", "h", "H")
and timestring[0].isnumeric()
):
if timestring[-1] in ("h", "H"):
t = int(timestring[:-1]) * 3600
elif timestring[-1] in ("m", "M"):
t = int(timestring[:-1]) * 60
else:
t = int(timestring[:-1])
elif timestring.isnumeric():
t = int(timestring)
else:
print("No time Provided")
except ValueError:
print("Error Value")
return t
This solution is working, However, I was wondering how can I do this more shorter and more efficiently.
CodePudding user response:
Extract the hours, minutes and seconds and then use datetime.timedelta like this:
from datetime import timedelta
ts = "1h:1m:30s"
time_indicators = ["H", "h", "M", "m", "S", "s"]
for ind in time_indicators:
ts = ts.replace(ind, "")
hours, minutes, seconds = ts.split(":")
print(timedelta(hours=int(hours), minutes=int(minutes), seconds=int(seconds)).total_seconds())
CodePudding user response:
If you want to catch bad user input - using split then a regex:
import re
UNIT_TO_SECONDS = {
'h': 3600,
'm': 60,
's': 1
}
def parse_part(part):
match = re.match(r'^(\d )([HhMmSs])$', part)
if match is None:
raise ValueError(f'"{part}" is not a valid part of time')
return (int(match.group(1)),match.group(2).lower() )
def to_seconds_part(part):
nb, unit = parse_part(part)
return nb * UNIT_TO_SECONDS[unit]
def to_seconds(user_input):
parts = user_input.split(':')
parts_seconds = list(map(to_seconds_part, parts))
return sum(parts_seconds)
