Reputation: 57
So I have for example the following while statements and I would like to combine them. Because this can get tiresome if you have 20 of these with all different if statements.
while True:
name = str(raw_input("NAME PLEASE\n"))
if name.isalpha():
break
print("Please chars dude")
while True:
age = raw_input("Please type your age\n")
if age.isdigit():
break
print("Please digits only")
If I combine them and someone types a A-Z character with 'age' then the code restarts all over without having saved the 'name' statement. I would like it to save 'name' if it's correct and only start over from the if statement that was false.
while True:
name = str(raw_input("NAME PLEASE\n"))
if name.isalpha():
break
print("Please chars dude")
age = raw_input("Please type your age\n")
if age.isdigit():
break
print("Please digits only")
Upvotes: 2
Views: 1284
Reputation: 1452
Yes, you can combine both loops in one loop!
Always try to solve the problem line by line.
You will get to learn the language better and it is the most simple way to solve any problem too.
A line by line solution would look like this:
name = '' # define name outside while loop
while True:
if not name:
name = str(raw_input("NAME PLEASE\n"))
if not name.isalpha(): # validate name
print("Please chars dude")
# reset name
name = ''
else:
age = raw_input("Please type your age\n")
if age.isdigit(): # validate age
"""continue your code here"""
print('name: ' + name + ' and age: ' + age)
print('Ok! Goodbye!')
break # while loop
else:
print("Please digits only")
will print:
NAME PLEASE
Elis
Please type your age
30
name: Elis and age: 30
Ok! Goodbye!
This will help you understand while
loop better and how to use it in more difficult cases.
Do not over design using redundant language features. It will make refactoring and debugging difficult.
Upvotes: 0
Reputation: 257
So I have for example the following while statements and I would like to combine them. Because this can get tiresome if you have 20 of these with all different if statements.
I assume the actual problem is "How to reduce tiresome code?" instead of "How to merge two loops into one?". I think keeping two loops is a good idea.
def safe_input(prompt, err_message, validation_fn):
while True:
value = raw_input(prompt)
if validation_fn(value):
return value
print err_message
name = safe_input("NAME PLEASE\n", "Please chars dude", str.isalpha)
age = safe_input("Please type your age\n", "Please digits only", str.isdigit)
If you always want the used to enter text in a separate line, you might want to print prompt
before raw_input
and to not give an argument to raw_input
. That way you don't have to supply "\n"
in every call of safe_input
.
Upvotes: 0
Reputation: 1121356
Use a function to encapsulate asking for information. You can pass in a validation test function:
def ask(question, validator, errormessage):
while True:
result = raw_input(question)
if not validator(result):
print(errormessage)
continue
return result
name = ask("NAME PLEASE\n", lambda s: s.isalpha(), "Please chars dude")
age = ask("Please type your age\n", lambda s: s.isdigit(), "Please digits only")
This is far more readable then any number of tests to see if the user already entered a correct name and you only need to ask for the age now.
Upvotes: 4
Reputation: 1360
Try this:
name = None
age = None
while requires_info:
if name is None:
temp_name = str(raw_input("NAME PLEASE\n"))
if temp_name.isalpha():
name = temp_name
continue
else:
print("Please chars dude")
continue
if age is None:
temp_age = raw_input("Please type your age\n")
if temp_age.isdigit():
age = temp_age
continue
else:
print("Please digits only")
continue
break
What we do here is use a single continuous loop and a few if statements/variables to track what still needs to be done. Note depending on how you want them to enter the data you may also add logic to not ask for age if the name was invalid.
Upvotes: 0
Reputation: 11280
You can set the variables to None first, and then check them before assignment:
name, age = None, None
while True:
if name is None:
name = str(raw_input("NAME PLEASE\n"))
if not name.isalpha():
print("Please chars dude")
name = None
continue
if age is None:
age = raw_input("Please type your age\n")
if not age.isdigit():
print("Please digits only")
age = None
continue
print("input is valid")
break
continue will start the loop over again. This fits better in the logic of your code, since break actually stop and exit the loop code.
Upvotes: 1
Reputation: 46992
Why not use functions and cut down on some duplication in the process?
def ask_input(prompt, error_msg, validation_fn):
while True:
data = raw_input(prompt)
if validation_fn(data):
return data
print(error_msg)
name = ask_input("NAME PLEASE\n", "Please chars dude", lambda x: x.isalpha())
age = ask_input("Please type your age\n", "Please digits only",
lambda x: x.isdigit())
In this case, the prompt (what to ask the user), an error message (what to provide on invalid input), and a validation function are provided to the ask_input()
function. This hides the while loop behind the function call and gives you something more meaningful to read in the code.
The lambda functions are just an easy way to help do the validation. You could do this instead:
def isalpha(x):
return x.isalpha()
def isdigit(x):
return x.isdigit()
name = ask_input("NAME PLEASE\n", "Please chars dude", isalpha)
age = ask_input("Please type your age\n", "Please digits only", isdigit)
Upvotes: 3
Reputation: 1438
Just use flags to track weather valid input is given, if given then exit the loop.
name_input_required = True
name = ''
while name_input_required:
name = str(raw_input("NAME PLEASE\n"))
if name.isalpha():
name_input_required = False
else:
print("Please chars dude")
age_input_required = True
age = None
while age_input_required:
age = raw_input("Please type your age\n")
if age.isdigit():
age_input_required = False
else:
print("Please digits only")
Upvotes: 0