Python readability - python-2.7

Greetings stackoverflow,
I am pretty new to both this website and python.
I wrote a simple program to create a list of devisors based on a user inputted number, the program works (as far as I know)
But I am pretty sure my syntax is extremely amateurish, so I ask the fluent among you, what can I do to make this:
divisors = []
def devisors(x):
while True:
try:
for i in range(1,x+1):
if x%i==0:
divisors.append(i)
if x==i:
break
except ValueError, TypeError:
return "Invalid input."
continue
print "The list of divisors of",x,"Are: ", divisors
choice1= raw_input("Would you like to use devisors program?(Y/N): ")
while True:
try:
if choice1 in yes:
x = int(raw_input("Please enter a number: "))
devisors(x)
elif choice1 in no:
print "Alright, bye bye."
break
else:
print "invalid input"
choice1= raw_input("Would you like to use devisors program(Y/N): ")
continue
except ValueError, TypeError:
print "Invalid input, try again."
try:
choice2= raw_input("Would you like to try again?(Y/N): ")
if choice2 in yes:
divisors = []
continue
devisors(x)
elif choice2 in no:
print "Alright, bye bye. "
break
else:
print "invalid input"
choice2= raw_input("Would you like to try again?(Y/N): ")
continue
except ValueError, TypeError:
print "Invalid input, try again."
Better written?
I want you to go berserk on this code, tell me (If you feel like it) what could be done to improve it, to write less lines, and mistakes I made.
Also I am not sure if this is something allowed on stackoverflow, if not, please let me know and I'll delete this.
Thank you.
Looking forward to the feedback.

First of all, we do have a dedicated Stack Exchange Code Review site, but you're not the only one asking for a code review here.
The first thing I noticed is that you are trying to hard to put everything in a single method.
Whenever you are faced with a problem or task you should try to divide it into the smallest possible problems. Afterwards we can implement the solution to these small problems as functions.
In your example your tasks are the following:
Get user input of a number
Get the divisors of that number
Print the divisors
Ask if the user wants to give it another try
Let's start with the 2nd point of our list:
def divisors_of(x):
if x < 0:
raise ValueError("Value cannot be smaller than 0")
divisors = []
for i in range(1, x + 1):
if x % i == 0:
divisors.append(i)
return divisors
That doesn't look too bad, does it?
After implementing the user input for a number and printing the result, we already get something like this:
try:
num = int(raw_input("Please enter a number: "))
divisors = divisors_of(num)
print "The divisors of ", num, " are: ", divisors
except (ValueError, TypeError) as ex:
print ex.message
Looking at our task list we still don't ask the user for another try. Again, IMHO it's more readable if we put the logic for that in a function. This has two additional benefits, we can convert the yes/no choice to a boolean and the written code is reuseable:
def yes_no_choice(text):
while True:
choice = raw_input(text)
if choice in "yes":
return True
# Returning like this is called early return
# As we jump out of the function, the code after
# the if is automatically the else statement
# The code is shorter and more readable
if choice in "no":
return False
print "Invalid answer"
Our final result looks like this:
while True:
try:
num = int(raw_input("Please enter a number: "))
divisors = divisors_of(num)
print "The divisors of ", num, " are: ", divisors
except (ValueError, TypeError) as ex:
print ex.message
if not yes_no_choice("Would you like to try again?(Y/N): "):
print "Bye!"
break
# else we will loop
Oh, and try not to use global variables if you don't have to. I'm looking at your divisors = []

Related

What could be wrong with this lines of code?

choice = input("Which of this beautiful artwork would you like to buy? ").lower()
if choice == "GreenLeave":
print("Great choice")
else:
print("Ok")
#whenever I input "GreenLeave" in the console, it doesn't print the if statement which is "Great Choice" that I want it to, it goes ahead to print the else statement "Ok" instead, please help.

Python 2.7 - Raw_input and If and else

raw_input('What are you doing? ')
a = 'nothing'
if type(a):
print 'That seems boring'
else:
print 'Nice'
The meaning of this code, is that if a person answers the raw_input with 'nothing'. It should print that seems boring. And if a person writes something else it should print ok.
I am new to programming so please help me :)
If I understood your question correctly, what you are looking for is:
a = raw_input("What are you doing?")
Notice that the answer to the prompt is saved in the variable 'a'.
if a == 'nothing':
print 'That seems boring'
else:
print 'Nice'
Pay attention to the indentation. Also, we use '==' for comparison and '=' for assigning values to a variable.
I suggest you learn basics of python from https://www.codecademy.com/
I always like to make variables that show what they contain.
My version would look like this:
print "What are you doing?"
reply = raw_input()
if reply == "nothing":
print "That seems boring"
else:
print "Nice"
You can also do it like this, it will take input during run time in more oriented way
#!/usr/bin/env python
def user_input():
print "What are you doing?"
# takes user input
a = raw_input()
# if user enter "Nothing" or "nothing"
if (a == "Nothing") or (a == "nothing"):
print "boring"
# if he enters anything else
else:
print "nice"
if __name__ == '__main__':
user_input()

Using for loop within if statements in Python

I am really having a hard time with loop statements for python, please see below:
I want it to check the users age, so if they are over 18, it will say "old enough, if they are over 16, it will say "almost there" and if they are younger than this, it will say "sorry you're too young"
I got the following code below:
age = int(raw_input("Enter your age:"))
if age >= 18:
print "You are old enough!"
elif age >= 16:
print "Almost there"
else:
print "You're just too young"
my problem is, how do I write code the includes an if statement and a for loop that will print out all the numbers from 0 that are less than the user's inputted age?
do I say:
for age in range (0,num)
if num <= age
print ....
else:
print...
Please kindly help. I'm new at this and still learning :(
So you could construct a variable that contains a list of numbers that is smaller than the user's age. You can construct this using python's range function; something like range(age) would do this nicely.
Then you need to use a for loop to loop through all these numbers and print them to the command line. Something like for x in range(age) would be a good place to start.
Then, in the loop, you'd just need to turn x from an integer into a string using the str() function, and print it to the command line.
So as pseudo-code:
if the age is greater than 18:
print that they're old enough
else if the age is greater than 16:
print that they're nearly old enough
otherwise:
print that they're not old enough.
for each number between 0 and age:
print the number
Come back when you have some code and we can help you with any trouble you have.

How to create multiple loops in python

I'm trying to create a basic maths program which will randomly generate a numerical question and then allows 3 attempts to complete it before it moves onto the next question however cant figure out how to make it do both together.
My code currently looks like this
print "What is your name?"
score = 0
Attempt = 0
loop = True
Name = raw_input()
import random
for i in range (1,6):
question_1_part_1 = random.randint(1,30)
question_1_part_2 = random.randint(1,30)
print "What is", question_1_part_1, "+", question_1_part_2, "?"
while Attempt <3: # inputing this while loop here means it will retry the same question.
Guess = raw_input()
Guess = int(Guess)
answer = question_1_part_1 + question_1_part_2
if Guess == answer:
print "Well done"
score = score + 1
else: print "try again"
Attempt = Attempt + 1
if Attempt == 3: print "You failed"
print Name, "your score is", score
A simple break statement will take you out of the loop when the answer is correct.
if Guess == answer:
print "Well done"
score += 1
break
else: print "try again"
Note the change to your assignment; this is considered a cleaner increment.
To answer your comment ... you don't use this when the person gets the question wrong. Your program logic freezes out the user after three wrong guesses total, on all questions. If you want them to have up to three guesses on every problem, then you have to reset the Attempt counter for every question. Pull that line into the outer loop:
for i in range (1,6):
Attempt = 0
loop = True
question_1_part_1 = random.randint(1,30)
question_1_part_2 = random.randint(1,30)
In the future, I strongly recommend that you program incrementally: get a few lines working before you add more. Insert tracing print statements to check that the values and program flow are correct. Don't remove them until that part of the code is solid -- and even then only comment them out until the entire program is working. Some of your problems stem from trying to write more than you can comfortably hold in your mind at once -- which is common at most levels of programming. :-)
Add another argument to your while loop.
while Attempt <3 and Guess != ... :
rest of loop code
Then you are exiting your loop when they get the correct answer. Or you could break from the statement when they get the answer right.

Python input, ifstatement, return

I have to create a function that takes an input, and returns a corresponding Grade.
So for example if the user inputs A+ output is 90%
or
if the input is A output is 80%
or
if the input is B output is 70%
I have some sort of Idea on how to do this... but I am having trouble on wrapping my head around on how I can return the statement??
def percent (percentage):
if ( percentage )== A+
return ("90%")
elif (percentage)== A
return ("80%")
Is this the correct way of going about it?
OK, so first, welcome to Python. Second, this is Pythonic way of doing this - define a dict:
grades = {'A+': "90%", 'A': "80%", ...}
then
return grades[precentage]
will do the job.
You need to protect against the case where the grade is not in the dict, for example, if the user entered some mistake, like G. There are a few ways to go about that:
A simple if:
if precentage in grades:
return grades[precentage]
else:
return "bad precentage"
After you get used to Python you will be more aesthetic about your code and will want to do better than state twice bote grades and precentage, so you can do simply:
return grades.get(precentage, "bad precentage")
Or using a special dict with default values:
import collections
grades = collections.defaultdict(lambda: "bad precentage", [("A+", "90%"), ("A", "80%")])
then
grades[precentage]
will automatically return "bad precentage" upon bad input.
#user2829744 You don't want to have to repeatedly call if statements based on what the percentage is, that would make the code unnecessarily long.
Instead, you want to have a list or tuple (a variable which stores multiple elements) that the program can compare the user's inputted value to, and then calculate the percentage mark.
Take this for example:
def percentage(per):
grades=["A+","A","B","C","D","E","F"]
percentage=("90%","80%","70%","60%","50%","40%","30%")
for i in range(7):
if per.upper()==grades[i]:
return percentage[i]
d="a"
print(percentage(d))
What happens is that i counts up to the number seven, and if the value of i in grades (let's say i is 5, then that would be grades[5] which would be an "E") then the function returns the value of i in the percentage tuple. In my case, the interpreter outputs 80%
Logically, your way of going about it (by actually dealing with every grade possible in separate if statements) would work too, however like I said your code would be longer and chances are you'd make a few typos along the way that you'd have to edit. Of course, my code has a few problems too, like what if the user enters a grade which I don't have in the tuple. This is easily fixable though as you would just need to tell the interpreter what to do if that happens.
A bit brief I know, but I hope this helps
You could do something like this
user_input = int(input("percentage: ")
if user_input < 0 and user_input > 10:
print('F")
And then you can just duplicate the code and change the numbers and the return grade
Hope it helps :)