Как проверить операторы с целыми числами для программы-калькулятора?

Я пытаюсь создать программу, которая позволяет пользователю вводить один из четырех операторов (сложение, вычитание, умножение или деление), а затем два числа. Затем программа вычисляет операцию. Однако я не могу проверить операторы для вывода. Сейчас я пытаюсь использовать оператор if ... else, но безуспешно. Любые указатели здесь?

operator = ""
numbers = []
inputNumbers = ["first number", "second number"]

def userInput():
    try:
        operator = input("Please choose a valid operation (+, -, *, /): ")
    except:
        print("Please enter a valid operator.")
    for inputNumber in inputNumbers:
        user_num_input = -1
        while user_num_input < 0:
            try:
                user_num_input = int(input("Type in {}: ".format(inputNumber)))
            except:
                user_num_input = -1
                print("Please enter a whole number.")
            if user_num_input > -1:
                numbers.append(user_num_input)
userInput()

def addNumbers():
    add = numbers[0] + numbers[1]
    return add(numbers)

def subNumbers():
    sub = numbers[0] - numbers[1]
    return sub(numbers)

def mulNumbers():
    mul = numbers[0] * numbers[1]
    return mul(numbers)

def divNumbers():
    div = numbers[0] / numbers[1]
    return div(numbers)

def userOutput():
    if operator == "+":
        print(numbers[0], "+", numbers[1], "=", addNumbers())
    elif operator == "-":
        print(numbers[0], "-", numbers[1], "=", subNumbers())
    elif operator == "*":
        print(numbers[0], "*", numbers[1], "=", mulNumbers())
    elif operator == "/":
        print(numbers[0], "/", numbers[1], "=", divNumbers())
userOutput()

person Kyle Barnes    schedule 08.12.2018    source источник


Ответы (3)


Вы должны проверить, ввел ли пользователь действительную операцию, try except здесь не сработает, так как input() не выдаст никаких ошибок. Также есть более элегантный способ получить 2 действительных целых числа от пользователя и вычислить окончательное уравнение (используя eval())

inputNumbers = ["first number", "second number"]
operations = ['+', '-', '*', '/']

numbers = []
operator = ''

while not operator:
    operator = input('Please choose a valid operation (+, -, *, /): ')
    if operator not in operations:
        print("Please enter a valid operator.")

while len(numbers) < len(inputNumbers):
    try:
        numbers.append(int(input("Type in {}: ".format(inputNumbers[len(numbers)]))))
    except:
        print("Please enter a whole number.")

result = eval(operator.join(map(str, numbers)))
print('{} {} {} = {}'.format(numbers[0], operator, numbers[1], result))

Вывод:

Please choose a valid operation (+, -, *, /): addition
Please enter a valid operator.
Please choose a valid operation (+, -, *, /): /
Type in first number: 123.321
Please enter a whole number.
Type in first number: 10 
Type in second number: hundred
Please enter a whole number.
Type in second number: 100
10 / 100 = 0.1
person Filip Młynarski    schedule 08.12.2018
comment
Я бы не стал использовать eval для такой обыденной задачи, тем более, когда вы оцениваете ввод пользователя, так что это не рекомендуется. Более того, у нас есть модуль operator, готовый к использованию, как в моем ответе: stackoverflow.com/a/53686331/10642035 - person Luan Naufal; 08.12.2018
comment
Почему вы думаете, что это не рекомендуется при оценке пользовательского ввода? Это более надежное и элегантное решение, чем делать все вручную. - person Filip Młynarski; 08.12.2018
comment
Элегантный наверняка выглядит лучше. Проблема с использованием `eval()` заключается в том, что мы должны знать о риске того, что в процессе производства некоторый вредоносный код может быть внедрен с использованием этого поля input. Не то, чтобы бояться в контексте этой проблемы, но что-то, что определенно важно упомянуть. - person Luan Naufal; 08.12.2018
comment
@FilipMłynarski, вы действительно думаете, что это решение более элегантно, чем другие со встроенным модулем? - person Attila Bognár; 08.12.2018

Вам следует использовать встроенный operator модуль Python. Затем вы можете использовать dict следующим образом:

import operator

operator_dict = {"+": operator.add, 
                 "-": operator.sub, 
                 "*": operator.mul,
                 "/": operator.truediv}
user_input = input("Please choose a valid operation (+, -, *, /): ")
operator_func = operator_dict.get(user_input, None)
# if operator_func is not None then the input was correct!
if operator_func is not None:
    ... get the numbers ...
    print("{}{}{}={}".format(num1, user_input, num2, operator_func(num1, num2))

Таким образом, вам не нужно самостоятельно реализовывать простую функциональность оператора.

person Attila Bognár    schedule 08.12.2018

Самый простой и чистый способ сделать это — использовать модуль operator в Python, поэтому ваш метод userOutput будет выглядеть следующим образом. Однако несколько изменений, которые вы должны внести в свой код, заключаются в переименовании переменной hour operator в op, поскольку это будет конфликтовать с именем модуля Python, и обновлении operator в качестве возврата из userInput():

import operator
op = ""
numbers = []
inputNumbers = ["first number", "second number"]
operators = {
        '+' : operator.add,
        '-' : operator.sub,
        '*' : operator.mul,
        '/' : operator.truediv,
        '%' : operator.mod,
        '^' : operator.xor,
}

def userInput(op):
    while not op:
        op = input("Please choose a valid operation (+, -, *, /): ")
        if op not in operators:
            print("Please enter a valid operator.")
            op = ""
    for inputNumber in inputNumbers:
        user_num_input = -1
        while user_num_input < 0:
            try:
                user_num_input = int(input("Type in {}: ".format(inputNumber)))
            except:
                user_num_input = -1
                print("Please enter a whole number.")
            if user_num_input > -1:
                numbers.append(user_num_input)
    return op

def userOutput(op, operators):
    result = operators[op](numbers[0], numbers[1])
    print("{} {} {} = {}". format(numbers[0], op, numbers[1], result))

op = userInput(op)
userOutput(op, operators)
person Luan Naufal    schedule 08.12.2018
comment
Вы используете модуль operator в качестве ключа, и ваша функция не имеет никаких аргументов для передачи пользовательского ввода! - person Attila Bognár; 08.12.2018
comment
Вы правы, @AttilaBognár, обновленный с полным кодом, теперь учитывающий все аспекты его правильной работы. - person Luan Naufal; 08.12.2018
comment
теперь лучше, но все еще есть некоторые проблемы с блоком первой попытки. Подумайте, что происходит, когда пользователь вводит недопустимую операцию... - person Attila Bognár; 08.12.2018
comment
@AttilaBognár, первая часть кода была именно той, которую написал @KyleBarnes. Поскольку проблема заключалась в том, чтобы иметь дело с оператором, это было единственное, над чем я работал. В любом случае обновил первую часть, убрав try / except, чтобы работать правильно, пока не будет введено действительное operator. - person Luan Naufal; 09.12.2018