2016-10-26 1 views
-2

Вот код для калькулятора в Python:Упрощая код - выполнять математические операции, основанные на операторе

import time 
#Returns the sum of num1 and num2 
def add(num1, num2): 
    return num1 + num2 

#Returns the difference of num1 and num2 
def subtract(num1, num2): 
    return num1 - num2 

#Returns the quotient of num1 and num2 
def divide(num1, num2): 
    return num1/num2 

#Returns the product of num1 and num2 
def multiply(num1, num2): 
    return num1 * num2 

#Returns the exponentiation of num1 and num2 
def power(num1, num2): 
    return num1 ** num2 

import time 

def main(): 
    operation = input("What do you want to do? (+, -, *, /, ^): ") 
    if(operation != "+" and operation != "-" and operation != "*" and operation != "/" and operation != "^"): 
     #invalid operation 
     print("You must enter a valid operation") 
     time.sleep(3) 
    else: 
     var1 = int(input("Enter num1: ")) #variable one is identified 
     var2 = int(input("Enter num2: ")) #variable two is identified 
     if(operation == "+"): 
      print (add(var1, var2)) 
     elif(operation == "-"): 
      print (subtract(var1, var2)) 
     elif(operation == "/"): 
      print (divide(var1, var2)) 
     elif(operation == "*"): 
      print (multiply(var1, var2)) 
     else: 
      print (power(var1, var2)) 
main() 
input("Press enter to exit") 
exit() 

Около 30 минут назад я нашел свою старую папку Python и взглянул на все мои основные сценарии из 8 + месяцев назад. Я нашел мини-скрипт для калькулятора и подумал, что было бы интересно воссоздать его как можно меньше строк (я только сейчас изучаю лямбду). Вот что у меня есть:

main = lambda operation,var1,var2: var1+var2 if operation=='+' else var1-var2 if operation=='-' else var1*var2 if operation=='*' else var1/var2 if operation=='/' else 'None' 
print(main(input('What operation would you like to perform? [+,-,*,/]: '),int(input('Enter num1: ')),int(input('Enter num2: ')))) 
input('Press enter to exit') 

Я знаю, что это личный вопрос, основанный с моей конкретной ситуации, но я был бы признателен за любую помощь, что делает его короче. Есть ли способ сделать его более Pythonic? Я правильно использую лямбду? Есть ли способ обработки ошибок в моей сокращенной версии? Любая помощь будет оценена по достоинству. Я очень новичок в этом. Благодаря!

+1

Чтобы сделать его более вещий, поставить методы обратно и сделать его читаемым человеком – Sayse

+0

Кроме того, может быть более подходящим для [codereview.se], но проверить свои руководящие принципы, прежде чем отправлять – Sayse

+0

@Adler: Добавлен ответ. Это то, что тебе надо? Отметьте ответ как принятый, если вы достигли того, что хотите, чтобы другие смотрели на него в будущем как ссылка –

ответ

0

Чтобы упростить код, я предлагаю:

  1. Создать функцию для выполнения операции приема помощи словаря.

    Примечание: Я отклоняю альтернативу с помощью функции lambda, основанной на требовании, указанном пользователем. Лично я хотел бы использовать operator

    Использование operator:

    import operator 
    
    def perform_operation(my_operator): 
        return { 
         '+': operator.add, 
         '-': operator.sub, 
         '*': operator.mul, 
         '/': operator.truediv, # "operator.div" in python 2 
         '^': operator.pow, 
        }.get(my_operator, '^') # using `^` as defualt value since in your 
              # "else" block you are calculating the `pow` 
    

    Использование lambda:

    def perform_operation(my_operator): 
        return { 
         '+': lambda x, y: x + y, 
         '-': lambda x, y: x - y, 
         '*': lambda x, y: x * y, 
         '/': lambda x, y: x/float(y), 
         '^': lambda x, y: x ** y, 
        }.get(my_operator, '^') # using `^` as defualt value since in your 
              # "else" block you are calculating the `pow()` 
    

    Пример запуска:

    >>> perform_operation('/')(3, 5) 
    0.6 
    

    PS: Глядя на Defination вы получили бы идея, почему используя operator более вещий, чем lambda

  2. Обновление else блока, чтобы позвонить ему как:

    var1 = int(input("Enter num1: ")) 
    var2 = int(input("Enter num2: ")) 
    perform_operation(operation)(var1, var2) # Making call to function created above 
    # THE END - nothing more in else block 
    
  3. Упростите if состояние с:

    if operation not in ["+", "-", "*", "/", "^"]: 
        # invalid operation 
    
+0

Вау, спасибо! Я не знал о «операторе», он делает все гораздо проще для интерпретации. В будущем я обязательно буду использовать его. Лямбда сбивает с толку, и часто бывает трудно читать. Я ценю ответ. –

0

Я понимаю, что это интересный самообман (и я впечатлен тем, насколько хорошо вы его сжали), но я мог бы также дать общий совет по лямбде и питоничности, как вы просили. Используйте их только при создании встроенного кода.

PEP-8 предлагает единственное преимущество использования лямбда в том, что они могут быть встроены в большее выражение. Например:

result = sorted(some_weird_iterable, key=lambda x: abs(x[0] - x[-1])) 

Если вы хотите присвоить идентификатор метода, всегда используйте def, потому что это дает вам ценную информацию трассировки стека и понимания. На самом деле, если это что-то, что выходит за рамки самого тривиального случая, я бы предложил избегать лямбда полностью, чтобы яснее понять, что вы делаете.

def as_the_bird_flies_distance(x): 
    return abs(x[0] - x[-1]) 

result = sorted(some_weird_iterable, key=as_the_bird_flies_distance) 

Концепция создания чего-то более «Питонического» не должна сокращать его. Но чтобы было легче читать, поддерживать и расширять.

Python 2.7.11 (default, Jan 22 2016, 08:29:18) 
[GCC 4.2.1 Compatible Apple LLVM 7.0.2 (clang-700.1.81)] on darwin 
Type "help", "copyright", "credits" or "license" for more information. 
>>> import this 
The Zen of Python, by Tim Peters 

Beautiful is better than ugly. 
Explicit is better than implicit. 
Simple is better than complex. 
Complex is better than complicated. 
Flat is better than nested. 
Sparse is better than dense. 
Readability counts. 
Special cases aren't special enough to break the rules. 
Although practicality beats purity. 
Errors should never pass silently. 
Unless explicitly silenced. 
In the face of ambiguity, refuse the temptation to guess. 
There should be one-- and preferably only one --obvious way to do it. 
Although that way may not be obvious at first unless you're Dutch. 
Now is better than never. 
Although never is often better than *right* now. 
If the implementation is hard to explain, it's a bad idea. 
If the implementation is easy to explain, it may be a good idea. 
Namespaces are one honking great idea -- let's do more of those! 
+0

Спасибо за подсказку. Когда я впервые обнаружил «лямбда», я нашел его в файле pygame в выражении. Я был смущен, почему кто-то беспокоился о том, чтобы сделать вещи более сложными, чем они должны были быть, но теперь я вижу. Лямбда полезна, потому что она позволяет избежать прыжков (и может быть встроена в одну строку, как вы сказали), но это запутывает, когда создаваемая вами функция не проста. Это идея лямбды? Спасибо, что ответили. Я, наконец, понимаю, почему более длинный, более промежуточный код является предпочтительным. –

+0

@ AdlerWeber определенно. Если лямбда не поможет с ясностью, не используйте ее. Это сделает ваш код сложнее отлаживать и просто путать вас, когда вы вернетесь, и попытайтесь изменить его позже. – SCB