Breaking/continuing out of multiple loops

I’m referring to reconsidering the logic - something that’s broader than any form of simplistic, “one size fits all” solution. I agree the try/except approach is not good. I disagree strongly with your idea that naming a block of code (i.e., “single use functions”) is unacceptable - naming a subexpression in a complex calculation is fine, why is naming a block of code in a complex loop any less acceptable? And yes, I’d often refactor by naming the inner loop. Or I might refactor by merging the 2 loops into one using a generator. Or something else. Basically I’d think about the code and what it was trying to do, and as I say, I’d nearly always find a better approach.

Think of it in terms of “having to break out of multiple loops is a code smell, indicating that you should re-think your approach”.

It does if you simply call the function stuff or something equally passive-aggressively unhelpful. But if you think about the logic, part of that is thinking about how to describe parts of the process, and that usually results in a good name.

Of course not all code warrants that much effort. A lot of my code is quick hacks. But even in that case, I can usually find a better way than “exit from 2 loops”.

I don’t think everyone piling in with their code samples is particularly helpful. The most recent example I had, though, was a “try to fetch a URL 10 times before giving up” loop, inside the body of a function. I wanted to break out if one of the tries returned a 304 Not Modified status. A double-break would have worked. But in reality, stopping and thinking for a moment and factoring out the inner loop into a fetch_url function was far better, named the operation in a way that was more readable, and made the outer loop shorter and hence more readable itself.

OK, so you’ve been lucky enough to not have had my experience. How many real life examples of code using labelled breaks have you seen (obviously they wouldn’t have been in Python, as there’s no labelled break in Python)? Were they all easy to read, and easy to maintain? How big (in terms of numbers of lines) were the loops? My experience suggests that the feature is not a particular problem for short loops (less than 10 lines, like most constructed examples) but scales badly to loops that are tens or hundreds of lines long[1].

However, I’ll also note that this is irrelevant (see your comment above about getting back on topic). Python doesn’t have labelled breaks (or any kind of multiple breaks). The debate isn’t about how they might be problematic, it’s about what value they have that justifies adding them to the language. The onus is very much on you (and anyone else in favour of the proposal) to argue why they benefit users, in the first instance. If we get to the point where there’s a clear understanding of the benefits, then (and only then) is there a point to discussing whether the (perceived) problems are important enough to outweigh the benefits.

So please, can we stick to the point here. What are the benefits of this syntax? Clearly it lets you do something that at the moment can’t be done without some form or refactoring of the code. But how important is that? How much real world code (not theoretical examples, or code written to demonstrate a point) would be improved by this feature? Even if I concede (which I don’t - but as I say that’s not the point yet) that multi-level breaks are perfectly fine for readability and maintainability, you still need to demonstrate that there’s a need, and it’s not just a neat idea that no-one actually needs. Otherwise the status quo wins.


  1. Yes, I know loops that long are unmaintainable anyway. That’s why having some pressure to refactor them helps… ↩︎

2 Likes