⚡ Phase 2 · Control Flow 🟢 Beginner MODULE 06

Conditional Statements

⏱️ 35 min read
📖 Theory + Code
🧩 5 Quiz Questions
🏗️ 1 Challenge
Phase 2 progress17%
🎯 What you'll learn: How Python makes decisions with if, elif, and else. How indentation defines code blocks. Nested conditionals, the ternary (one-line if), truthy/falsy values, and how to avoid the most common if/else mistakes.

What Are Conditionals?

Every real program needs to make decisions. Conditional statements let your program run different code depending on whether a condition is True or False. Without them, every program would do exactly the same thing every time — no intelligence, no interactivity.

Python uses three keywords: if (the question), elif (else-if — more questions), and else (the fallback when nothing matches).

💡
Indentation IS the syntax
Unlike most languages that use { } curly braces, Python uses indentation to define code blocks. Every line inside an if block must be indented by the same amount — conventionally 4 spaces. Wrong indentation = IndentationError or silent logic bugs.
if condition:← colon is required
do this if condition is True← 4-space indent
elif another_condition:← optional, as many as needed
do this instead
else:← optional, no condition needed
do this if nothing matched
if_basic.py
PYTHON
temperature = 38

# Simple if
if temperature > 37:
    print("You have a fever.")   # runs — 38 > 37 is True

# if / else
age = 16
if age >= 18:
    print("You can vote.")
else:
    print("Too young to vote.")  # runs — 16 >= 18 is False

# if / elif / else — multiple branches
score = 74
if score >= 90:
    print("Grade: A")
elif score >= 75:
    print("Grade: B")
elif score >= 60:
    print("Grade: C")    # runs — 74 is >= 60 but not >= 75
else:
    print("Grade: F")
⚠️
elif chains stop at the first True
Python evaluates if / elif top-to-bottom and stops the moment one condition is True. Even if later conditions would also be true, they are skipped. This is why the order of your elifs matters — always put the most specific condition first.

Indentation — Python's Core Rule

Indentation in Python is not a style choice — it is the syntax. The interpreter uses indentation to determine which statements belong to which block. You must be consistent. The standard is 4 spaces (not a tab, not 2 spaces — 4).

❌ IndentationError
if age >= 18:
print("adult")  # no indent!

if score > 50:
    print("pass")
      print("well done") # extra indent!
✅ Correct Indentation
if age >= 18:
    print("adult")  # 4 spaces

if score > 50:
    print("pass")     # 4 spaces
    print("well done") # same level
Use a code editor, not Notepad
VS Code, PyCharm, or even IDLE auto-indent for you when you press Enter after a colon. They also highlight mismatched indentation instantly. Never write Python in a basic text editor — you'll waste hours debugging invisible indent issues.

Combining Conditions

Use and, or, and not to build complex multi-part conditions inside an if statement. You already know these operators from Lesson 4 — now they become the backbone of your program logic.

combined_conditions.py
PYTHON
age       = 22
has_id    = True
is_banned = False

# and — both must be True
if age >= 18 and has_id:
    print("Entry allowed.")

# or — at least one True
if age < 12 or age > 60:
    print("Discounted ticket.")

# not — invert
if not is_banned:
    print("Account is active.")

# Combined — real login check
username = "admin"
password = "secure123"
attempts = 2

if username == "admin" and password == "secure123" and attempts <= 3:
    print("✅ Login successful!")
elif attempts > 3:
    print("🔒 Account locked — too many attempts.")
else:
    print("❌ Wrong username or password.")

# Chained comparison — very Pythonic
bmi = 22.5
if 18.5 <= bmi < 25.0:
    print("Normal weight range.")

Nested Conditionals

You can place an if statement inside another if statement. This is called nesting. It's useful when a second decision only makes sense after a first condition is confirmed.

Be careful though — deeply nested code quickly becomes hard to read. A common rule is to avoid going more than 2–3 levels deep. If you find yourself deeper, use and to flatten the logic, or functions (Phase 3).

nested_if.py
PYTHON
is_registered = True
has_paid      = True
seat_number   = 14

if is_registered:
    print("User found in system.")
    if has_paid:
        print("Payment confirmed.")
        if seat_number <= 50:
            print("🎫 Front section. Enjoy the event!")
        else:
            print("🎫 Back section. Enjoy the event!")
    else:
        print("⚠️  Payment not received. Please pay first.")
else:
    print("❌ User not found. Register first.")

# ─────────────────────────────────────────────
# Better approach for simple nesting: use 'and'
if is_registered and has_paid and seat_number <= 50:
    print("🎫 Front section. Enjoy the event!")
🎭
Early return / guard clause pattern
Professional Python code often uses a "guard clause" — check the failure condition first and exit early. This flattens nesting dramatically: if not is_registered: print("Not found"); exit() — then the rest of the code can run without nesting. You'll use this constantly once you learn functions.

Truthy & Falsy Values

In Python, any value can be used as a condition — not just booleans. Python automatically treats values as True (truthy) or False (falsy). This is one of Python's most elegant features.

Falsy — treated as False
False   0   0.0   ""   None   []   {}   ()
Any zero, empty collection, or None
Truthy — treated as True
Everything else: non-zero numbers, non-empty strings, non-empty lists, any object. 42   "hi"   [1,2] are all truthy.
truthy_falsy.py
PYTHON
# Checking for empty string (Pythonic way)
username = input("Enter username: ").strip()
if username:              # True if not empty
    print(f"Welcome, {username}!")
else:
    print("Username cannot be empty.")

# Checking for None (use 'is')
result = None
if result is None:
    print("No result yet.")

# Checking non-zero
items_in_cart = 3
if items_in_cart:         # True because 3 != 0
    print(f"{items_in_cart} items in your cart.")

# Common pattern: default value when empty
name = input("Name (or press Enter): ").strip()
display_name = name if name else "Anonymous"
print(f"Hello, {display_name}!")

Ternary Expression — One-Line If

Python has a concise one-line conditional expression called a ternary (or conditional expression). It's perfect when you want to assign one of two values based on a condition — without writing a full 4-line if/else block.

Syntax: value_if_true if condition else value_if_false

ternary.py
PYTHON
# Traditional if/else
age = 20
if age >= 18:
    status = "adult"
else:
    status = "minor"

# Same thing as a ternary — one line
status = "adult" if age >= 18 else "minor"
print(status)     # adult

# Ternary inside f-string
score = 72
print(f"Result: {'Pass' if score >= 50 else 'Fail'}")  # Pass

# Ternary with absolute value
n = -7
absolute = n if n >= 0 else -n
print(absolute)   # 7

# Pass/fail label for report card
pf = lambda m: "✅ Pass" if m >= 50 else "❌ Fail"
print(pf(85))    # ✅ Pass
print(pf(32))    # ❌ Fail
⚠️
Don't overuse ternary — readability first
Ternary is great for simple value assignment. But x if a > b and c != d else y if e else z is unreadable. If a ternary is hard to read at a glance, use a regular if/else block instead. Clarity beats cleverness every time.

Real-World Conditional Patterns

Let's look at the patterns professional Python developers use most often when writing conditionals.

real_patterns.py
PYTHON
# ── Pattern 1: Input validation guard ────────
age_raw = input("Enter age: ")
if not age_raw.isdigit():
    print("Age must be a number.")
else:
    age = int(age_raw)
    print(f"Age: {age}")

# ── Pattern 2: Range classification ──────────
bmi = 26.4
if   bmi < 18.5:  cat = "Underweight"
elif bmi < 25.0:  cat = "Normal"
elif bmi < 30.0:  cat = "Overweight"   # 26.4 lands here
else:              cat = "Obese"
print(f"BMI {bmi}: {cat}")

# ── Pattern 3: Membership check ──────────────
role    = "editor"
allowed = ["admin", "editor", "moderator"]
if role in allowed:
    print("Access granted.")
else:
    print("Access denied.")

# ── Pattern 4: Fizz-Buzz (classic interview Q)
n = 15
if   n % 15 == 0: print("FizzBuzz")  # check divisible by BOTH first
elif n % 3  == 0: print("Fizz")
elif n % 5  == 0: print("Buzz")
else:               print(n)
FizzBuzz — understand it cold
FizzBuzz is the most common screening question in coding interviews. The key insight: check divisibility by 15 (both 3 and 5) first, then 3, then 5. If you check 3 first, 15 would match it and never reach FizzBuzz. Order matters.
🧩 Knowledge Check
5 questions — test your mastery of Conditional Statements
1. What character is required at the end of every if, elif, and else line?
2. Which values are considered falsy in Python?
3. What is the output of this code?
x = 15
if x > 10: print("A")
elif x > 5: print("B")
else: print("C")
4. What does "pass" if score >= 50 else "fail" represent?
5. In Python, how are code blocks defined inside if statements?
🏗️
Coding Challenge — ATM Simulator
Build a complete decision tree using nested and combined conditions
Task: Build a simple ATM Simulator that:

1. Stores a PIN (e.g. 1234) and a balance (e.g. 25000) as variables
2. Asks the user to enter their PIN — if wrong, print "Incorrect PIN" and stop
3. If PIN is correct, show a menu: 1) Check Balance   2) Withdraw   3) Deposit
4. For Withdraw: check if amount is positive AND ≤ balance; deduct if valid, warn if not
5. For Deposit: check if amount is positive; add if valid, warn if not
6. Print the updated balance after any transaction using currency formatting
💡 Show hints
  • Use int(input("PIN: ")) and compare with stored PIN
  • Use nested if/elif/else — outer checks PIN, inner checks menu choice
  • Withdraw condition: amount > 0 and amount <= balance
  • Format balance: f"PKR {balance:,.2f}"
atm_simulator.py — Sample Solution
PYTHON
# ── ATM Simulator ─────────────────────────────
CORRECT_PIN = 1234
balance     = 25000.0

print("=" * 36)
print("       🏧  ATM MACHINE")
print("=" * 36)

pin = int(input("Enter PIN: "))

if pin != CORRECT_PIN:
    print("❌ Incorrect PIN. Access denied.")
else:
    print("✅ PIN accepted.")
    print("\n  1) Check Balance")
    print("  2) Withdraw")
    print("  3) Deposit")
    choice = input("\nSelect (1/2/3): ").strip()

    if choice == "1":
        print(f"\n  💰 Balance: PKR {balance:,.2f}")

    elif choice == "2":
        amount = float(input("  Withdraw amount: PKR "))
        if amount <= 0:
            print("  ❌ Amount must be positive.")
        elif amount > balance:
            print(f"  ❌ Insufficient funds. Balance: PKR {balance:,.2f}")
        else:
            balance -= amount
            print(f"  ✅ Withdrawn PKR {amount:,.2f}")
            print(f"  💰 New balance: PKR {balance:,.2f}")

    elif choice == "3":
        amount = float(input("  Deposit amount: PKR "))
        if amount <= 0:
            print("  ❌ Deposit must be positive.")
        else:
            balance += amount
            print(f"  ✅ Deposited PKR {amount:,.2f}")
            print(f"  💰 New balance: PKR {balance:,.2f}")
    else:
        print("  ❌ Invalid option.")
🎉
Lesson 6 Complete!
You can now make programs that think and decide. Next — loops to make them repeat!
← Course Home
Phase 2 · Control FlowLesson 6 of 6