[英]Python: Calling a function inside another function with returned values: Error Handling?
我创建了以下Python模块,该模块将24小时(00:00到23:59)转换为单词。 Function1()在尝试提取12小时,分钟和句点之前测试输入的字符串是否与正确的24小时格式匹配(即am =“中午之前”和pm =“中午之后”)。 下面的代码可以完美地用作一个独立的函数,但是当我从function3()调用它时,当输入字符串与正确的格式不匹配并且try语句不执行时,失败,因此不会返回返回值。 由于以下返回值不存在,因此Function3()失败。 如何重组function1(),以便在模式不匹配时,Python模块停止运行,仅执行function1()中的else语句,让最终用户知道输入字符串与正确的格式不匹配?
"""
Created on 29 May 2017
Convert 24hr format time
into time as words
@author: PeterW
"""
# import site-packages and modules
import re
import time
import argparse
def function1(input_time):
"""convert time from 24hr format
into 12hours, minutes, period"""
period_type = {'AM': 'before midday', 'PM': 'after midday'}
regexp_object = re.compile(r'^(([01]\d|2[0-3]):([0-5]\d)|23:59)$')
if regexp_object.match(input_time):
try:
time_object = time.strptime(input_time, '%H:%M')
suffix = time.strftime('%p', time_object)
hours = int(time.strftime('%I', time_object))
minutes = time_object[4]
period = period_type.get(suffix)
print("{0}:{1} {2}".format(hours, str(minutes).zfill(2), period))
return hours, minutes, period
except ValueError as err:
print(err)
else:
print("{0} doesn't match required format 00:00 to 23:59"
.format(input_time))
def function2():
"""create dictionary
to lookup equivalent word
of integer number"""
words_lookup = {1: 'one', 2: 'two', 3: 'three', 4: 'four', 5: 'five',
6: 'six', 7: 'seven', 8: 'eight', 9: 'nine', 10: 'ten',
11: 'eleven', 12: 'twelve', 13: 'thirteen',
14: 'fourteen', 16: 'sixteen', 17: 'seventeen',
18: 'eighteen', 19: 'nineteen', 20: 'twenty',
21: 'twenty one', 22: 'twenty two', 23: 'twenty three',
24: 'twenty four', 25: 'twenty five', 26: 'twenty six',
27: 'twenty seven', 28: 'twenty eight', 29: 'twenty nine'}
return words_lookup
def function3(input_time):
"""convert 24hr format time
into time as words"""
hours, minutes, period = function1(input_time)
words_lookup = function2()
if hours == 12:
hours2 = words_lookup.get(1)
else:
hours2 = words_lookup.get(hours+1)
if hours == 12 and minutes == 0 and period == 'before midday':
time = 'Midnight'
elif hours == 12 and minutes == 0 and period == 'after midday':
time = 'Midday'
elif minutes == 0:
time = "{0} o'clock {1}.".format(str(words_lookup.get(hours)).title(),
period)
elif minutes == 15:
time = "Quarter past {0} {1}.".format(words_lookup.get(hours),
period)
elif minutes == 30:
time = "Half past {0} {1}.".format(words_lookup.get(hours),
period)
elif minutes == 45:
time = "Quarter to {0} {1}.".format(hours2,
period)
elif minutes < 30:
minutes = str(words_lookup.get(minutes)).capitalize()
time = "{0} minutes past {1} {2}.".format(minutes,
words_lookup.get(hours),
period)
else:
minutes = str(words_lookup.get(60 - minutes)).capitalize()
time = '{0} minutes to {1} {2}.'.format(minutes,
hours2,
period)
print(time)
if __name__ == '__main__':
parser = argparse.ArgumentParser(description="Convert 24hr format time into time as words")
parser.add_argument('--input_time', metavar='string', required=True,
help='input time in following format 00:00 to 23:59')
args = parser.parse_args()
function3(input_time=args.input_time)
最终版本如下,感谢您的帮助。
"""
Created on 04 June 2017
Convert 24hr format time
into time as words
@author: PeterW
"""
# import site-packages and modules
import sys
import re
import time
import argparse
def validate_time_format(input_time):
"""Validate that input string
matches require 24hr time format"""
regexp_object = re.compile(r'^(([01]\d|2[0-3]):([0-5]\d)|23:59)$')
if regexp_object.match(input_time):
print("Processing: {0} into words".format(input_time))
time_str = input_time
else:
print("{0} doesn't match required input format: 00:00 to 23:59".format(input_time))
sys.exit()
return time_str
def extract_time(time_str):
"""convert time from 24hr format
into 12hours, minutes, period"""
period_type = {'AM': 'before midday', 'PM': 'after midday'}
try:
time_object = time.strptime(time_str, '%H:%M')
suffix = time.strftime('%p', time_object)
hours = int(time.strftime('%I', time_object))
minutes = time_object[4]
period = period_type.get(suffix)
# print("{0}:{1} {2}".format(hours, str(minutes).zfill(2), period))
return hours, minutes, period
except ValueError as err:
print(err)
def time_lookup():
"""create dictionary
to lookup equivalent word
of integer number"""
words_lookup = {1: 'one', 2: 'two', 3: 'three', 4: 'four', 5: 'five',
6: 'six', 7: 'seven', 8: 'eight', 9: 'nine', 10: 'ten',
11: 'eleven', 12: 'twelve', 13: 'thirteen',
14: 'fourteen', 16: 'sixteen', 17: 'seventeen',
18: 'eighteen', 19: 'nineteen', 20: 'twenty',
21: 'twenty one', 22: 'twenty two', 23: 'twenty three',
24: 'twenty four', 25: 'twenty five', 26: 'twenty six',
27: 'twenty seven', 28: 'twenty eight', 29: 'twenty nine'}
return words_lookup
def time_as_words(input_time):
"""convert 24hr format time
into time as words"""
time_str = validate_time_format(input_time)
hours, minutes, period = extract_time(time_str)
words_lookup = time_lookup()
if hours == 12:
hours2 = words_lookup.get(1)
else:
hours2 = words_lookup.get(hours+1)
if hours == 12 and minutes == 0 and period == 'before midday':
time = 'Midnight'
elif hours == 12 and minutes == 0 and period == 'after midday':
time = 'Midday'
elif minutes == 0:
time = "{0} o'clock {1}.".format(str(words_lookup.get(hours)).title(),
period)
elif minutes == 15:
time = "Quarter past {0} {1}.".format(words_lookup.get(hours),
period)
elif minutes == 30:
time = "Half past {0} {1}.".format(words_lookup.get(hours),
period)
elif minutes == 45:
time = "Quarter to {0} {1}.".format(hours2,
period)
elif minutes < 30:
min_str = str(words_lookup.get(minutes)).capitalize()
time = "{0} minute{1} past {2} {3}.".format(min_str,
"" if minutes == 1 else "s",
words_lookup.get(hours),
period)
else:
min_str = str(words_lookup.get(60 - minutes)).capitalize()
time = '{0} minute{1} to {2} {3}.'.format(min_str,
"" if 60 - minutes == 1 else "s",
hours2,
period)
print(time)
if __name__ == '__main__':
parser = argparse.ArgumentParser(description="Convert 24hr format time into time as words")
parser.add_argument("-t", "--input_time", metavar="time", type=str, required=True,
help='input time in the following format 00:00 to 23:59')
args = parser.parse_args()
time_as_words(input_time=args.input_time)
当function1
失败时,它隐式返回None
。 呼叫者必须意识到这种可能性:
retval = function1(input_time)
if retval is None:
# do something - say, exit
else:
hours, minutes, period = retval
将if regexp_object.match(input_time)
切换为if not regexp_object.match(input_time)
,并同时切换逻辑:
def function1(input_time):
"""convert time from 24hr format
into 12hours, minutes, period"""
period_type = {'AM': 'before midday', 'PM': 'after midday'}
regexp_object = re.compile(r'^(([01]\d|2[0-3]):([0-5]\d)|23:59)$')
# Switch to checking if it isn't valid instead, and exit early if that's the case
if not regexp_object.match(input_time):
print("{0} doesn't match required format 00:00 to 23:59"
.format(input_time))
exit(-1)
# Since we already returned if the regex didn't match, we know if it reaches this point it'll match
try:
time_object = time.strptime(input_time, '%H:%M')
suffix = time.strftime('%p', time_object)
hours = int(time.strftime('%I', time_object))
minutes = time_object[4]
period = period_type.get(suffix)
print("{0}:{1} {2}".format(hours, str(minutes).zfill(2), period))
return hours, minutes, period
except ValueError as err:
print(err)
请注意, exit
实际上是完全退出程序。 如果您只想将某个内容(例如None
,以表示出现问题)返回到另一个函数,则可以改return None
然后该函数将在那儿返回。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.