Error Handling with Try/Except
Catching exceptions gracefully with try/except/else/finally instead of letting a program crash.
2 min read
Things go wrong at runtime — a file doesn't exist, a user types text where a number was expected, a network call times out. Python's try/except lets a program respond to that instead of crashing outright.
The basic pattern
try:
age = int(input("Enter your age: "))
print(f"You are {age} years old.")
except ValueError:
print("That's not a valid number.")Python runs the try block; if a ValueError is raised anywhere inside it, execution jumps straight to the matching except block instead of crashing the program with a traceback.
Catching specific exceptions
Catch the narrowest exception type that applies, rather than a bare except: that swallows everything:
try:
result = 10 / 0
except ZeroDivisionError:
print("Can't divide by zero.")
except ValueError:
print("Invalid value.")# Avoid -- hides bugs you'd want to know about
try:
risky_operation()
except:
passA bare except: catches everything, including typos in your own code (like a misspelled variable name raising NameError) and even KeyboardInterrupt when a user presses Ctrl+C. That makes real bugs silently disappear instead of surfacing where you can fix them.
Accessing the exception itself
try:
value = int("not a number")
except ValueError as e:
print(f"Conversion failed: {e}")as e binds the actual exception object to a name, letting you inspect its message or log it rather than just knowing that something failed.
else and finally
try:
number = int("42")
except ValueError:
print("Invalid input")
else:
print(f"Parsed successfully: {number}")
finally:
print("Done attempting to parse.")else runs only if the try block completed with no exception — useful for code that should run on success but shouldn't itself be wrapped in the same try (and therefore accidentally caught if it fails). finally always runs, whether an exception occurred or not, and is the standard place for cleanup like closing a file or a network connection.
Raising your own exceptions
def withdraw(balance, amount):
if amount > balance:
raise ValueError("Insufficient funds")
return balance - amount
try:
withdraw(100, 150)
except ValueError as e:
print(e) # Insufficient fundsraise lets your own functions signal a problem using the same mechanism, so callers can handle it with the same try/except pattern rather than checking a special return value.
The rule of thumb
Use exceptions for genuinely exceptional situations — a missing file, invalid input, a failed network call — not for routine control flow that an if check would handle more clearly. Reserving try/except for real error conditions keeps it meaningful when it does appear in your code.
Test what you just learned
4 quick questions. Get all of them right to unlock the next lesson.
You can take the quiz without an account — logging in just lets your result count toward your progress.