#python #exception #math
#python #исключение #математика
Вопрос:
Я создаю код для решения квадратичной формулы и нуждаюсь в обработке исключений, чтобы были обнаружены отсутствующие аргументы командной строки. В except IndexError:
блоке вместо выхода из программы вы должны использовать input()
, чтобы запросить у пользователя недостающие входные данные. Это не работает со следующим кодом. У кого-нибудь есть идеи?
from math import sqrt
import sys
print('This program will solve the quadratic formula with given values, please enter below.')
try:
a=float(sys.argv[1]) #first system argument
b=float(sys.argv[2]) #second system argument
c=float(sys.argv[3]) #third system argument
d=b**2-4*a*c #discriminant
x1=((-b sqrt(d))/2*a) #first solution
x2=((-b-sqrt(d))/2*a) #second solution
except IndexError:
raise IndexError(
'Oops! Looks like you have not entered all values. Try again.') #request user input
a=input(sys.argv[1]) #first system argument
b=input(sys.argv[2]) #second system argument
c=input(sys.argv[3]) #third system argument
d=b**2-4*a*c #discriminant
x1=((-b sqrt(d))/2*a) #first solution
x2=((-b-sqrt(d))/2*a) #second solution
print(f'The quadratic formula with used a,b,c values gives two roots {x1:.2f} and {x2:.2f}')
Комментарии:
1. Вы перехватили исключение и снова вызвали его. Удалить
raise IndexError
.2.
sys.argv
это список, содержащий все заданные аргументы командной строки. Если вы не указали правильные аргументы при запуске программы, они волшебным образом не появятся, как только вы попытаетесь обработать исключение. Вместо этого изучите использованиеinput()
для взаимодействия с пользователем.3. После того, как вы попали в
except
блок, с вами поконченоsys.argv
. Вы запрашиваете у пользователя значение напрямую. Проще всего просто выйти из программы и заставить пользователя передать правильные аргументы в первую очередь.4. Используйте
argparse
модуль для обработки аргументов командной строки (и связанных с ними ошибок).5. Прежде чем делать что-либо еще, проверьте длину
sys.argv
и убедитесь, что было предоставлено правильное количество аргументов, а если нет, используйтеinput()
для их получения ) или просто распечатайте сообщение об ошибке и завершите работу).
Ответ №1:
Я вижу несколько способов улучшить исходный код:
- Следующие инструкции
raise
никогда не выполняются - Преобразование строки через
float()
может вызватьValueError
- Если указано менее 3 аргументов, то
sys.argv[n]
будет выдана ошибка - Вы должны повторно проверять повторно введенные входные данные, пока они не станут правильными.
- Вы не должны запускать повторный ввод правильных значений, если у более поздних возникают проблемы.
- Если ваш дискриминант d отрицательный,
sqrt()
выдастValueError
- Сделайте свой код СУХИМ (не повторяйтесь), разложив логику проверки.
- Вам нужен какой-то способ сделать вывод.
Следующий код исправляет это с помощью:
- Добавление метода validate для более СУХОГО и проверки ввода и обработки
ValueError
. - Обработайте 3 аргумента по порядку с помощью итератора, который возвращает » если не указан, который будет обрабатывать метод validate.
- Тест на отрицательный дискриминант.
from math import sqrt
import sys
print('This program will solve the quadratic formula with given values, please enter below.')
def validate(name, value):
try:
return float(value)
except ValueError:
new_value = input(f"Entered a value for {name}: ")
return validate(name, new_value)
args = iter(sys.argv)
a = validate('a', next(args, ''))
b = validate('b', next(args, ''))
c = validate('c', next(args, ''))
d=b**2-4*a*c #discriminant
if d >= 0 :
x1=((-b sqrt(d))/2*a) #first solution
x2=((-b-sqrt(d))/2*a) #second solution
print(f"the roots {x1} and {x2}")
else:
print("the equation has no real-valued solutions")
Ответ №2:
Вы создаете исключение un внутри блока catch:
except IndexError:
raise IndexError(
'Oops! Looks like you have not entered all values. Try again.')
Вы можете удалить его и запросить у пользователя это сообщение, используя input() или что-то подобное. например:
except IndexError:
a= input('Oops! Looks like you have not entered all values. Enter the value again.')