3
while True:
    input = raw_input("enter input: ")
    result = useInput(input)

def useInput(input):
    if input == "exit":
        break   #return 0 / quit / etc.. i want to break the while loop from within this function

I know I can put the "if logic" directly in the while loop, but I want it to be in the function. Is there a way to break a while loop from within a function called in the loop?

2
  • 1
    Is this just proof of concept, because the logic is very convoluted for what you're trying to do? Commented Jan 25, 2013 at 14:09
  • The idea is that the function should handle/process/format the input then return the result, BUT for some keywords (like "exit" or "pass") I need to affect the while loop by somehow calling "break" or "continue". Aesthetically, I didn't like the idea of having all of these exceptions/keywords directly in the loop. But I am new to all this, so perhaps I just don't know the "proper" style to do it.. Commented Jan 25, 2013 at 17:37

5 Answers 5

3
  1. Raise an exception, that you can handle outside the While loop
  2. Return a flag to be captured by the caller and handle accordingly. Note, "if logic" directly in the while loop,, would be the most preferred way.
Sign up to request clarification or add additional context in comments.

Comments

2

Python has a cool feature in generators - these allow you to easily produce iterables for use with a for loop, that can simplify this kind of code.

def input_until(message, func):
    """Take raw input from the user (asking with the given message), until 
    when func is applied it returns True."""
    while True:
        value = raw_input(message)
        if func(value):
            return
        else:
            yield value

for value in input_until("enter input: ", lambda x: x == "exit"):
    ...

The for loop will loop until the iterator stops, and the iterator we made stops when the user inputs "exit". Note that I have generalised this a little, for simplicity, you could hard code the check against "exit" into the generator, but if you need similar behaviour in a few places, it might be worth keeping it general.

Note that this also means you can use it within a list comprehension, making it easy to build a list of results too.

Edit: Alternatively, we could build this up with itertools:

def call_repeatedly(func, *args, **kwargs):
    while True:
        yield func(*args, **kwargs)

for value in itertools.takewhile(lambda x: x != "exit", 
                                 call_repeatedly(raw_input, "enter input: ")):
    ...

Comments

1

I usually do this:

def getInput():
    while True:
        yield raw_input("enter input: ")

for input in getInput():
    if input == 'exit': 
        break
    result = useInput(input)

Comments

0

You can raise an exception and handle it outside of while ... but that will likely result in some confusing code ...

def useInput(in_):
    if in_ == "exit":
        raise RuntimeError
try:
    while True:
        input = raw_input("enter input: ")
        result = useInput(input)

except RuntimeError:
    pass

It's MUCH better to just return a boolean flag and then break or not depending on the value of that flag. If you're worried that you already have something you want to return, don't fret -- python will happily let your function return more than one thing:

def func()
    ...
    return something,flag

while True:
    something,flag = func()
    if flag:
        break

Comments

0

Well if its just aesthetics thats keeps you from putting it in the while loop then any of the above would work... not of fan of the try/except one though. Just know there isn't going to be any performance difference putting it in its own function though. Here's one that I believe also meets your requirements :-)

# you have to define the function first if your while isn't in a function
def UseInput():
   input = raw_input("enter input: ")
   if input == "exit":
      return False
   elif input == "pass":
      return True


   # Do stuff
   return True


while UseInput():
   pass

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.