
The optional “else” in Python loops - s16h
http://shahriar.svbtle.com/pythons-else-clause-in-loops
======
Psyonic
While in theory this is useful, it's one of the least intuitive parts of
python for me. I avoid them whenever possible because I feel "else" conveys
the intent very poorly. (And I've been writing python for years.)

~~~
wting
Raymond Hettinger has suggested that instead of `else:` the keyword should
have been called `nobreak:` which conveys intentions better.

~~~
avn2109
What about using "finally," which if IIRC is already a thing in Python and
encapsulates this idea pretty neatly?

~~~
dbarlett
finally blocks are always executed; this kind of else block is only executed
if the for block exited normally (i.e. did not throw an exception).

~~~
aperture
How about a keyword such as "after"? I feel like that could have extensible
potential in other areas of the language, and the name makes a little sense
logically speaking.

~~~
gingerrr
or something like "then"?

------
agrover
Raymond Hettinger, one of the main Python devs, advises that the "else" in
this situation should mentally be thought of as "notfound".

~~~
eddyg
Glad you posted this. I came to the comments to post the same thing[1] because
thinking of it as "notfound" makes remembering (and comprehending it) easier.
:)

[1]
[https://www.youtube.com/watch?v=OSGv2VnC0go#t=17m12s](https://www.youtube.com/watch?v=OSGv2VnC0go#t=17m12s)

~~~
agrover
Ah, I misremembered, "nobreak", not "notfound".

------
kazinator
This badly named else is reminiscent of the "result forms" in Lisp loops like
`dolist`, `do` or `loop`.

    
    
        (loop for x below 10
                    finally (princ "iterated over everything, ") (princ "indeed"))
    

But, of course, these Lisp loops have a result value, and the result forms are
an "implicit progn" which produces that value.

------
ddandd
Not only it is not very intuitive, I also find it to hurt the linearity of
code. The code which will be executed after the loop ends depends on how the
loop ended. break statement is usually a glorified but mostly harmless go to,
but I think Python's go to statement isn't so harmless as it adds complexity
but doesn't have big benefits.

But, I do think that the else clause on try\except blocks is less harmful. It
is less harmful because the control flow complexity of exceptions handling is
already there on the catch clause, so while exceptions _does_ add big control
flow changes, the addition of the else clause causes a relative minor change
on the linearity of code (as it is already broken by catch: clause.)

------
gejjaxxita
I always strongly discourage the use of things like this construct in any
language.

A language is meant to be read not just written. A non-expert python
programmer who encounters this will be confused.

~~~
solox3
There will always be non-expert programmers of many languages. Avoiding
language-specific constructs will not solve the issue.

As far as portability is concerned (if you port software by hand a lot, for
example), this is indeed an issue; but if you work with people who write
python code, you might as well use everything in your toolbox.

~~~
pyre
> There will always be non-expert programmers of many languages. Avoiding
> language-specific constructs will not solve the issue.

This is a language-specific issue that occurs rarely in the wild. Yes, it's
part of the language, but it's used rarely enough that it can trip up even
experienced Python programmers.

For example, Perl (until more recently) allowed one to change arrays to be
1-indexed, rather than 0-indexed at runtime. Just because it's part of the
language doesn't mean that it's a good thing to use it.

------
bashwork
Created an account to point out this gem by Guido himself that makes use of
this and the fact that python variables are not scoped inside for loops:

[https://github.com/aosabook/500lines/blob/master/crawler/cra...](https://github.com/aosabook/500lines/blob/master/crawler/crawling.py#L100)

~~~
ludwik
Oh my God! I would be so confused reading this code!

------
gomesnayagam
it clear to me that this notion is not maintainable at all after looking the
comments though it is nice feature to have.

------
mdaniel
For me, the optional else on for loops isn't nearly as mentally destabilizing
as the optional else on try-except blocks. An ex-employee used to _love_ doing
that:

    
    
        try:
            None.doit()
        except Exception as e:
            logger.exception('Nope')
        else:
            # now what?
            pass

~~~
edavis
try/except/else used to throw me, but I've grown to like the idiom.

All it means is the try clause didn't raise any exceptions. And a "finally"
clause is ran whether an exception was raised or not.

------
mhd
Also known as "Dijkstra's loop" to give credit where credit is due. Only other
language I know that has it though is Oberon (and that just introduced it in a
pretty _recent_ update)

------
parham
Might be worth while looking at the video below for more Pythonic gems like
this one.

[https://www.youtube.com/watch?v=OSGv2VnC0go](https://www.youtube.com/watch?v=OSGv2VnC0go)

------
jw2013
This is all in Jeff Knupp's Writing Idiomatic Python:

[http://www.jeffknupp.com/blog/2012/10/04/writing-
idiomatic-p...](http://www.jeffknupp.com/blog/2012/10/04/writing-idiomatic-
python/)

Many so-called Python Idioms are really non-intuitive and I don't really
appreciate.

~~~
abuddy
They are intuitive and very easy to understand and read the code.

If you use Python you should code in Python, not trying to translate C to
Python.

------
enesunal
I would choose `finally` keyword over the `else`.

