else in Python: the remaining case of a condition

else handles the case the previous conditions let through. Python gives it three uses: after an if, after a loop, and after a try.
5 min read
Believemy logo

Definition

The moment a program asks a question, it has to know what to do with both answers. A payment goes through or it does not, and the declined case deserves handling just as much as the other. You could write a second if carrying the opposite condition, but those two tests always drift apart in the end: someone edits the first, forgets the second, and you are left with a gap or with two branches running one after the other.

else removes that risk. It introduces the block that runs when the structure it belongs to did not take its main path. Attached to an if, it covers every case the previous conditions let through, without you having to name them.

PYTHON
if balance >= amount:
    approve_payment()
else:
    decline_payment()

Notice that no condition follows the word else, and that nothing is missing for all that: whatever was not caught above lands here by construction. That is why an else can never open a structure, only close one.

A single branch runs, never both. That guarantee is worth more than it looks: after the structure, you can state that the variable has received a value whichever path was taken. Two independent if statements promise nothing of the sort.


The loop else, Python's surprise

Here is a nuisance everyone has met. You walk through a list looking for an item and leave with break as soon as you find it. Once the loop is over, how do you know whether you left because the search succeeded, or because the list ran out? The usual reflex is to set a boolean flag before the loop and read it back afterwards.

Python offers something shorter. for and while accept an else too, and many experienced developers still do not know it. That block runs when the loop reached its end without ever meeting a break.

PYTHON
for user in users:
    if user.email == wanted:
        print("Found")
        break
else:
    # Reached only if no break happened
    print("No user with that email")

The name is a poor one, nobody argues otherwise, and "nobreak" would have described the thing more faithfully. Read it this way: the loop finished its walk without leaving early. The flag lines disappear, and the intent becomes visible at the exact spot where it plays out.

One detail decides everything: only break cancels that block. A continue jumps to the next iteration without cancelling anything, and the else will still run at the end. A return, on the other hand, leaves the whole function, so nothing after the loop is reached. The while obeys the same rule: its else runs when the condition turns false, and is skipped when a break cuts it short.


The try else

The third use answers a very concrete trap. When a try wraps five lines, the except below watches all five, including the ones that had no reason to fail that way. An error coming from the processing then passes for an error opening the file, and you spend a long time looking in the wrong place.

The else block of a try runs only when no exception was raised. It comes after the last except, and before the finally if there is one.

PYTHON
try:
    handle = open("data.csv")   # The only line actually watched
except FileNotFoundError:
    print("File missing")
else:
    process(handle)             # Runs only if opening succeeded
finally:
    print("Done")               # Runs in every case

Everything that does not need watching therefore moves down into the else, and the try shrinks to the risky operation. What you gain is an honest diagnosis: the day that except fires, you know the file really is to blame.

Warning

An exception raised inside the else is not caught by the except written right above it: it travels up as if the try were not there. The behaviour is intended, but it does surprise you the first time you meet it in production.


When to do without it

An else is not always the right answer. The most frequent case is a function that starts by ruling out invalid inputs before doing its real work.

PYTHON
# With else: the real work is pushed one level in
def bill(client):
    if client.is_active:
        return compute(client)
    else:
        return 0

# Without else: rule out the faulty case, leave, and the rest breathes
def bill(client):
    if not client.is_active:
        return 0
    return compute(client)

The second form keeps the nominal case at the shallowest indentation, where the eye looks for it first. The return closes the faulty branch just as firmly as an else, without nesting anything behind it.

On a function ruling out four doubtful inputs before working, the gap becomes considerable: on one side a body buried under four levels of nesting, on the other four guards lined up on the left, then the processing. The same code does not read the same way at all.


Frequently asked questions

Question

Is an else required after an if?

No, a lone if is perfectly valid and very common: when there is nothing to do in the opposite case, write nothing. The else becomes necessary as soon as a variable must receive a value in every case, otherwise it stays undefined on the uncovered paths and the next line will raise an error.

Question

Why does my loop else never run?

Because a break was met somewhere in the loop, and that is the only thing which cancels the block. A single break hidden in a rarely satisfied condition is enough to create the surprise. A loop running over an empty sequence does run its else: zero iterations, therefore no break.

Question

What is the difference between else and elif?

elif introduces a new test, else introduces none. A chain can hold as many elif branches as needed but only one else, always in last position since it collects whatever is left. A branch written after it would never be reached.

Related terms

Discover our python glossary

Browse the terms and definitions most commonly used in development with Python.

Share this article

Want to help us? Share this article on your networks or even better: on your site, in an article or in your newsletter.