Python Exception Handling - try except finally with Examples
Errors and Exceptions
Python has two kinds of errors: syntax errors (caught before running) and exceptions (occur at runtime). Exceptions can be caught and handled gracefully using try/except.
Common Built-in Exceptions
| Exception | When it occurs |
|---|---|
ValueError | Wrong value type: int("abc") |
TypeError | Wrong type: "2" + 2 |
IndexError | List index out of range |
KeyError | Dict key not found |
AttributeError | Object has no such attribute |
NameError | Variable not defined |
ZeroDivisionError | Division by zero |
FileNotFoundError | File doesn't exist |
ImportError | Module not found |
StopIteration | Iterator exhausted |
RuntimeError | Generic runtime error |
OverflowError | Numeric result too large |
try / except
# Basic try/except
try:
result = 10 / 0
except ZeroDivisionError:
print("Cannot divide by zero!")
# Catch multiple exceptions
try:
value = int(input("Enter a number: "))
result = 100 / value
print(f"Result: {result}")
except ValueError:
print("That's not a valid number!")
except ZeroDivisionError:
print("Cannot divide by zero!")
# Catch multiple in one line
try:
x = int("abc")
except (ValueError, TypeError) as e:
print(f"Error: {e}")
# Catch any exception (use sparingly)
try:
risky_operation()
except Exception as e:
print(f"Something went wrong: {e}")
print(f"Error type: {type(e).__name__}")
else and finally
try:
file = open("data.txt", "r")
content = file.read()
except FileNotFoundError:
print("File not found!")
else:
# Runs only if NO exception occurred
print(f"File content: {content}")
finally:
# ALWAYS runs - perfect for cleanup
print("Done (with or without error)")
# file.close() would go here
# Real-world pattern: file handling
try:
with open("data.txt", "r") as f: # 'with' auto-closes the file
data = f.read()
except FileNotFoundError as e:
print(f"Error: {e}")
except PermissionError:
print("No permission to read this file")
else:
print(f"Read {len(data)} characters")
finally:
print("File operation complete")
Raising Exceptions
def set_age(age: int):
if not isinstance(age, int):
raise TypeError(f"Age must be an int, got {type(age).__name__}")
if age < 0 or age > 150:
raise ValueError(f"Age {age} is out of valid range (0-150)")
return age
try:
set_age(-5)
except ValueError as e:
print(f"ValueError: {e}")
# Re-raise an exception
try:
result = 10 / 0
except ZeroDivisionError as e:
print("Logging the error...")
raise # re-raises the same exception
# Raise from another exception (exception chaining)
try:
data = int("abc")
except ValueError as e:
raise RuntimeError("Failed to process data") from e
Custom Exceptions
# Custom exceptions inherit from Exception
class InsufficientFundsError(Exception):
def __init__(self, amount: float, balance: float):
self.amount = amount
self.balance = balance
super().__init__(
f"Cannot withdraw ${amount:.2f}. Balance: ${balance:.2f}"
)
class BankAccount:
def __init__(self, balance: float = 0):
self.balance = balance
def withdraw(self, amount: float):
if amount > self.balance:
raise InsufficientFundsError(amount, self.balance)
self.balance -= amount
return self.balance
account = BankAccount(100)
try:
account.withdraw(150)
except InsufficientFundsError as e:
print(f"Error: {e}")
print(f"Tried to withdraw: ${e.amount}")
print(f"Available: ${e.balance}")
Level Up Your Python Skills
Master Python with these hand-picked resources
10,000+ learners
Free forever
Updated 2026
Related Python Topics