Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Break or exit out of "with" statement?

People also ask

Can you break out of an if statement C++?

And depending on the situation, you could try a switch block instead; they do support breaking. If it's within a function, you could use "return".

How do you do a break in an if statement in Python?

Python break statement The break statement terminates the loop containing it. Control of the program flows to the statement immediately after the body of the loop. If the break statement is inside a nested loop (loop inside another loop), the break statement will terminate the innermost loop.

How do you break out of a loop in Python?

In Python, the break statement provides you with the opportunity to exit out of a loop when an external condition is triggered. You'll put the break statement within the block of code under your loop statement, usually after a conditional if statement.


with giving you trouble? Throw more with-able objects at the problem!

class fragile(object):
    class Break(Exception):
      """Break out of the with statement"""

    def __init__(self, value):
        self.value = value

    def __enter__(self):
        return self.value.__enter__()

    def __exit__(self, etype, value, traceback):
        error = self.value.__exit__(etype, value, traceback)
        if etype == self.Break:
            return True
        return error

Just wrap the expression you're going to with with fragile, and raise fragile.Break to break out at any point!

with fragile(open(path)) as f:
    print 'before condition'
    if condition:
        raise fragile.Break
    print 'after condition'

Benefits of this setup

  • Uses with and just the with; doesn't wrap your function in a semantically misleading one-run 'loop' or a narrowly specialized function, and doesn't force you to do any extra error handling after the with.
  • Keeps your local variables available, instead of having to pass them to a wrapping function.
  • Nestable!

    with fragile(open(path1)) as f:
        with fragile(open(path2)) as g:
            print f.read()
            print g.read()
            raise fragile.Break
            print "This wont happen"
        print "This will though!"
    

    This way, you don't have to create a new function to wrap the outer with if you want both to break.

  • Doesn't require restructuring at all: just wrap what you already have with fragile and you're good to go!

Downsides of this setup

  • Doesn't actually use a 'break' statement. Can't win em all ;)

The best way would be to encapsulate it in a function and use return:

def do_it():
    with open(path) as f:
        print 'before condition'
        if <condition>:
            return
        print 'after condition'

This is an ancient question, but this is an application for the handy "breakable scope" idiom. Just imbed your with statement inside:

for _ in (True,):
    with open(path) as f:
        print 'before condition'
        if <condition>: break
        print 'after condition'

This idiom creates a "loop", always executed exactly once, for the sole purpose of enclosing a block of code inside a scope that can be broken out of conditionally. In OP's case, it was a context manager invocation to be enclosed, but it could be any bounded sequence of statements that may require conditional escape.

The accepted answer is fine, but this technique does the same thing without needing to create a function, which is not always convenient or desired.


I think you should just restructure the logic:

with open(path) as f:
    print 'before condition checked'
    if not <condition>:
        print 'after condition checked'

Since break can only occur inside a loop your options are somewhat limited inside the with to:

  • return (put "with" + associated statements inside function)
  • exit (bail from program - probably not ideal)
  • exception (generate exception inside "with", catch below)

Having a function and using return is probably the cleanest and easiest solution here if you can isolate the with and the associated statements (and nothing else) inside a function.

Otherwise generate an exception inside the with when needed, catch immediately below/outside the with to continue the rest of the code.

Update: As OP suggests in the comments below (perhaps tonuge in cheek?) one could also wrap the with statement inside a loop to get the break to work - though that would be semantically misleading. So while a working solution, probably not something that would be recommend).


f = open("somefile","r")
for line in f.readlines():
       if somecondition: break;
f.close()

I dont think you can break out of the with... you need to use a loop...

[edit] or just do the function method others mentioned