error handling issue in python - python

I want to print out ERROR if the variable sizeOfList is less than 0, not an integer, or greater than 1000. This is how I am handling these errors:
if sizeOfList > 1000 or not isinstance(sizeOfList,int) or sizeOfList < 0:
print "ERROR:"
sys.exit()
It works perfectly fine except for when the variable is equal to zero. It thinks this is an error when I really just want it to print out nothing. I am really confused on why this is happening and how to fix it. Any help would be greatly appreciated!

Im not exactly sure what you are trying to accomplish but this is one way.
>>> def test_list(input):
... tmp = input
... while True:
... if len(input)<=0:
... print "out of range"
... break
... else:
... print tmp.pop()
...
>>> l = [1,2,3,4,5,5,6]
>>> test_list(l)
6
5
5
4
3
2
1
out of range

But when it is zero "ERROR:" is printed and the program exits...why is this?
The only way this is possible with the following conditional:
sizeOfList > 1000 or not isinstance(sizeOfList,int) or sizeOfList < 0
Is if your "zero" value is actually a string. Try
type(sizeOfList)
before your code to verify this.
Edit:
Generally you don't want to care about the variable types. Try writing like so:
if !sizeOfList.isdigit():
print "Not a number!"
sys.exit()
if sizeOfList < 0 or sizeOfList > 1000:
print "Not in range!"
sys.exit()

Related

How can I limit the in put to 100 ?? Sorry if my coding style is bad , i just started [duplicate]

Hi I want to get a number from user and only except input within a certain range.
The below appears to work but I am a noob and thought whilst it works there is no doubt a more elegant example... just trying not to fall into bad habits!
One thing I have noticed is when I run the program CTL+C will not break me out of the loop and raises the exception instead.
while True:
try:
input = int(raw_input('Pick a number in range 1-10 >>> '))
# Check if input is in range
if input in range(1,10):
break
else:
print 'Out of range. Try again'
except:
print ("That's not a number")
All help greatly appreciated.
Ctrl+C raises a KeyboardInterruptException, your try … except block catches this:
while True:
try:
input = int(raw_input('Pick a number in range 1-10 >>> '))
except ValueError: # just catch the exceptions you know!
print 'That\'s not a number!'
else:
if 1 <= input < 10: # this is faster
break
else:
print 'Out of range. Try again'
Generally, you should just catch the exceptions you expect to happen (so no side effects appear, like your Ctrl+C problem). Also you should keep the try … except block as short as possible.
There are several items in your code that could be improved.
(1) Most importantly, it's not a good idea to just catch a generic exception, you should catch a specific one you are looking for, and generally have as short of a try-block as you can.
(2) Also,
if input in range(1,10):
would better be coded as
if 1 <= input < 10:
as currently function range() repeatedly creates a list of values form 1 to 9, which is probably not what you want or need. Also, do you want to include value 10? Your prompt seems to imply that, so then you need to adjust your call to range(1, 11), as the list generated will not include the upper-range value. and the if-statement should be changed to if 1 <= input <= 10:
You can use this code:
def read_int(prompt, min, max):
while True:
try:
val = int(input(prompt))
except ValueError:
print('Error: wrong input')
else:
if(min <= val < max): # this is faster
break
else:
print('Error: the value is not within permitted range (min..max)')
return val
v = read_int("Enter a number from -10 to 10: ", -10, 10)
print("The number is:", v)

Python Variable Understanding

I was writing this code and I can't seem to get it to work correctly.
There's no Syntax errors so I'm clear on that.
It just is not giving me the correct output I want.
Here's the code :
This is the out put I get when x = 5 :
Big!
Done!
This is the output I get when x = 1
Small!
Done!
This is what I get when x = anything other than 1 or 5
Done!
What I want it to do is when x = anything between 1-5 to output Small! then Done!
Or if it is between 5-infinity to output Big! then Done! but if the number is not 1 or 5 it just outputs Done!
What changes should I do to my code?
As pointed by a user in the previous answer, what you need to implement is an if-else ladder and use logical operator for the case when your output is specifically either 1 OR 5
x=6 # You can replace this by a user defined input using input()
if x==5 or x==1:
print("Done!")
elif x<5:
print("Small!")
print("Done!")
elif x>5:
print("Big!")
print("Done!")
else:
print("Enter a valid number!")
I checked with various test cases like 1, 5 , numbers between 1 and 5 and numbers greater than 5 and all seem to work fine.
Here's a sample output
x = 5
if x in range(6):
print('Small')
elif x >=6 :
print('Big')
print('Done')
Try this. The range function checks if the number is in between 0 and 6 i.e 0 to 5. Anything lesser than 0 will be ignored
The problem with your code is that you're just checking two conditions if x== 5 and if x == 1. The print statements will be executed only if this condition is satisfied.
Cheers
You can create a if-else ladder to achieve this
def determine_size(inp):
if inp == 1 or inp == 5:
print("Done")
elif 0 <= inp < 5:
print("Small")
print("Done")
elif inp > 6:
print("Big")
print("Done")
else:
print("Negative Input")
>>> determine_size(0)
Small
Done
>>> determine_size(100)
Big
Done
>>> determine_size(60)
Big
Done
>>>
>>> determine_size(3)
Small
Done
>>> determine_size(4)
Small
Done
You can also play around with the if-else statements per your objectives
x = 40
# at first check if x is greater than 1 and less than 5.
# Only then it is between 1 and 5.
if x >=1 and x<=5:
print('Small!')
# Now chek if x is greater than 5
elif x>5:
print('Big!')
print('Done!')
if you meant the above mentioned scenario mentioned in comment
try:
x=int(input("enter a number: "))
if x >=0 or x<=5:
print("Small")
print("Done")
elif x>=6:
print("big")
print("Done")
except ValueError:
print("Done")
here the block of code is written in try block, why i have written in try block if someone enter something which is not number then program will not crash and raise a exception.
if you are not familiar with elif syntax, we can have simple construction like this :-
try:
x=int(input("enter a number: "))
if x >=0 and x<=5:
print("Small")
print("Done")
else:
print("big")
print("Done")
except ValueError:
print("Done")
Here all I have done is to change the logical operator from or to and.

How do I limit user input to specific integers, and keep track of exceptions, in Python 2.7?

EDIT: The suggested duplicate is incredibly helpful in regards to basic input validation. While it does cover a lot, my specific problem (failing to assign int(evaluation) to a variable) is only explicitly addressed here. I'm marking this separately in case anyone else has made a similarly silly mistake :)
I've spent the last few weeks playing with Python 2.7 and having a lot of fun. To learn more about while loops, I've created a small script which asks the user for an integer between 1 and 10.
My goal is to then be able to respond to cases in which the user responds with unexpected input, like a non-integer, or an integer outside the specified range. I've been able to fix a lot of my issues with help from other StackOverflow threads, but now I'm stumped.
First, I created a variable, idiocy, to keep track of exceptions. (The script is supposed to be sassy, but until I get it working, I'm the one it's making fun of.)
idiocy = 0
while 1:
evaluation = raw_input("> ")
try:
int(evaluation)
if evaluation < 1 or evaluation > 10:
raise AssertionError
except ValueError:
idiocy += 1
print "\nEnter an INTEGER, dirtbag.\n"
except AssertionError:
idiocy += 1
print "\nI said between 1 and 10, moron.\n"
else:
if idiocy == 0:
print "\nOkay, processing..."
else:
print "\nDid we finally figure out how to follow instructions?"
print "Okay, processing..."
break
As you can see, I'm trying to handle two different errors -- a ValueError for the input type, and an AssertionError for the integer range -- and keep track of how many times they're raised. (Really, I only care about knowing whether or not they've been raised at least once; that's all I need to insult the user.)
Anyways, when I run the script in its current form, the error response works just fine ('dirtbag' for non-integers, 'moron' for out-of-range). The problem is that even when I input a valid integer, I still get an out-of-range AssertionError.
I suspect that my issue has to do with my while logic, but I'm not sure what to do. I've added a break here or there but that doesn't seem to help. Any suggestions or blatant errors? Again, total Python beginner here, so I'm half winging it.
//If anyone has simpler, cleaner, or prettier ways to do this, feel free to let me know too. I'm here to learn!
Your problem is you're not saving the int version of evaluation to evaluation like this:
idiocy = 0
while 1:
evaluation = raw_input("> ")
try:
evaluation = int(evaluation) <--- here
if evaluation < 1 or evaluation > 10:
raise AssertionError
except ValueError:
idiocy += 1
print "\nEnter an INTEGER, dirtbag.\n"
except AssertionError:
idiocy += 1
print "\nI said between 1 and 10, moron.\n"
else:
if idiocy == 0:
print "\nDid we finally figure out how to follow instructions?"
print "Okay, processing..."
else:
print "\nOkay, processing..."
If you wanted to track the types of exceptions raised, you could use collections.Counter for idiocy and change the code like this:
from collections import Counter
idiocy = Counter()
while 1:
evaluation = raw_input("> ")
try:
evaluation = int(evaluation)
if evaluation < 1 or evaluation > 10:
raise AssertionError
except ValueError as e:
idiocy[e.__class__] += 1
print "\nEnter an INTEGER, dirtbag.\n"
except AssertionError as e:
idiocy[e.__class__] += 1
print "\nI said between 1 and 10, moron.\n"
else:
if idiocy == 0:
print "\nDid we finally figure out how to follow instructions?"
print "Okay, processing..."
else:
print "\nOkay, processing..."
>>> idiocy
Counter({AssertionError: 2, ValueError: 3})
And you can access the error counts by key like idiocy[AssertionError]
You have int(evalutation), but you're not assigning it to anything.
Try
try:
evaluation = int(evaluation)
assert 0 < evaluation < 10
except ValueError:
...
except AssertionError:
Your range test can be refactored as
assert 1 <= evaluation <= 10
You could keep your insults in a dictionary
insults = {AssertionError : "\nI said between 1 and 10, moron.\n",
ValueError : "\nEnter an INTEGER, dirtbag.\n"
}
And write the try/except like this
try:
...
except (AssertionError, ValueError) as e:
print(insults[type(e)])
When you change the user input to an int, you need to assign it to something
evaluation = int(evaluation)
assert was meant for debugging - you are using it incorrectly.
You should use TypeError for non-integer repsonses - the type is wrong.
You use ValueError for responses outside of a range - the value is wrong
In your code:
int(evaluation) is not typecasting evaluation variable to int type. The output is:
> 2
<type 'str'>
I said between 1 and 10, moron.
Try this:
idiocy = 0
while 1:
try:
evaluation = int(raw_input("> "))
if evaluation < 1 or evaluation > 10:
raise AssertionError
except ValueError:
idiocy += 1
print "\nEnter an INTEGER, dirtbag.\n"
except AssertionError:
idiocy += 1
print "\nI said between 1 and 10, moron.\n"
else:
if idiocy == 0:
print "\nOkay, processing..."
else:
print "\nDid we finally figure out how to follow instructions?"
print "Okay, processing..."
break
By the way you can use tuple to store all your exceptions.
Example:
idiocy = 0
all_exceptions = (ValueError, AssertionError)
while 1:
try:
evaluation = int(raw_input("> "))
if evaluation < 1 or evaluation > 10:
raise AssertionError("\nI said between 1 and 10, moron.\n")
except all_exceptions as e:
idiocy += 1
print str(e)
else:
if idiocy == 0:
print "\nOkay, processing..."
else:
print "\nDid we finally figure out how to follow instructions?"
print "Okay, processing..."
break
Hope it helps.

My program is not printing out the message I want

I have written a prime number program and I'm having a trouble with printing out the message "Neither prime nor a composite" as below. I think my code is fine as it is. I'd highly appreciate any comment on this issue. Thank you, in advance
def prime_number():
a = input("Please enter a number:")
x = True
s = 0
for i in range(2, a):
while x:
if a%i == 0:
x = False
elif s:
print s,"Neither a prime nor a composite"
else:
x = True
if x:
print a,"is a prime number."
elif s:
print s,"Neither a prime nor a composite"
else:
print a,"is not a prime number."
prime_number()
Your variable s will stay equall to 0 which is equall to False forever, so there is no way that Your code is going to print "Neither a prime nor a composite"
Just like Chantwaffle said, you'll never get s equal to anything else than 0, because there's no code changing it to anything else. Also, if a <= 2 you'll never enter this for loop, and elif s is always False, since s is defined as 0 at the beginning. Rewrite that code thinking of what you want to achieve and what should be done to get it. Repair logic of this code.

python breaking if statement inside for loop

I want the if-statement to break if the condition is met, because currently if it isn't broken early then I get some mishaps in my code.
The problem is, I am not sure where to put the break. When I put it where it is shown here I get "Unexpected indent", but when I put it back a level I get an error with the else-statement saying "Invalid Syntax".
EDIT: THE IF IS INDENTED. It just didn't show up in the sites code blocks. I will try and fix it on the site.
#duck, what do you think I am trying to do? I am in my first weeks of a python course. I came here to help myself, not get my code trolled by you. If you can help me then I would appreciate the help, otherwise I don't need you telling to "learn how to code" when that's exactly what I am trying to do.
So I am not sure what to do. Any help would be appreciated.
def pTurn(CampLoc, AICampLoc, score, yourHits, cHits):
if yourHits < 5:
hGuess = int(raw_input("Enter a co-ordinate to air-strike: "))
print "Air-striking co-ordinate: %d" % hGuess
for cSpot in AICampLoc:
if hGuess == cSpot:
yConfirMsg = "Kill confirmed!!"
yourHits += 1
score += 100
AICampLoc.remove(hGuess)
break
else:
yConfirMsg= "No casualties"
You are missing an indent, as the other answer states, but also, you have a bunch of code that isn't needed. Your code can be simplified to this:
def pTurn(CampLoc, AICampLoc, score, yourHits, cHits):
if yourHits < 5:
hGuess = int(raw_input("Enter a co-ordinate to air-strike: "))
print "Air-striking co-ordinate: %d" % hGuess
yConfirMsg= "No casualties"
for cSpot in AICampLoc:
if hGuess == cSpot:
yConfirMsg = "Kill confirmed!!"
yourHits += 1
score += 100
AICampLoc.remove(hGuess)
break
Try this:
def pTurn(CampLoc, AICampLoc, score, yourHits, cHits):
if yourHits < 5:
#^This line ident is probably the offending line. ;)
hGuess = int(raw_input("Enter a co-ordinate to air-strike: "))
print "Air-striking co-ordinate: %d" % hGuess
for cSpot in AICampLoc:
if hGuess == cSpot:
yConfirMsg = "Kill confirmed!!"
yourHits += 1
score += 100
AICampLoc.remove(hGuess)
break
else:
yConfirMsg= "No casualties"
score = score #You may want to fix this, since the logic doesn't make sense
yourHits = yourHits #Fix this line as well. This is variable value assignment to the same variable.
If this doesn't work, another thing to consider is that you may be inadvertently mixing tabs and whitespace when you indent the leading spaces for your code. If so, convert all the tabs to spaces.
And, regarding the notes cited. Perhaps you meant to return those values? If so, you need to fix those logic errors.
UPDATE:
If you only have to break once and only once, then you should replace break with return.
If not, then you should capture the location, continue loop execution, and do whatever you have to do with that information.
#...
values = {}
all_values = []
for cSpot in AICampLoc:
if hGuess == cSpot:
yConfirMsg = "Kill confirmed!!"
yourHits += 1
score += 100
AICampLoc.remove(hGuess)
values['message'] = yConfirMsg
values['hits'] = yourHits
values['score'] = score
values['camploc'] = AICampLoc
all_values.append(values)
else:
yConfirMsg= "No casualties"
#...

Categories