For Loops

NoteQuestions
  • How do I make a program repeat an operation for every item in a collection?
NoteObjectives
  • Explain what a for loop does and when to use one.
  • Identify the collection, loop variable, and body in a for loop.
  • Trace the values of variables through each iteration of a loop.
  • Use the accumulator pattern to reduce a collection to a single value.

for loops repeat operations over a collection

Performing the same calculation on every value in a list — or every file in a directory — by writing out each step individually is impractical. A for loop instructs Python to execute a block of statements once for each item in a collection, automatically advancing to the next item after each pass:

for number in [2, 3, 5]:
    print(number)
2
3
5

This is exactly equivalent to three separate print calls, but scales to thousands of items without any extra code.

Anatomy of a for loop

Every for loop has three parts:

  • The collection — the sequence of values to iterate over (here [2, 3, 5]).
  • The loop variable — the name that receives the current item on each pass (here number). It is created automatically and can be named anything, but a descriptive name makes the code easier to read.
  • The body — the indented block of statements that runs once per item.

The first line must end with a colon. Python uses indentation — not braces or keywords — to mark where the body begins and ends. Four spaces is the universal convention:

for number in [2, 3, 5]:
print(number)   # missing indentation
  Cell In[2], line 2
    print(number)   # missing indentation
    ^
IndentationError: expected an indented block after 'for' statement on line 1

Unexpected indentation is also an error — every line in a block must line up consistently:

firstName = "Jon"
  lastName = "Smith"   # unexpected extra indent
  Cell In[3], line 2
    lastName = "Smith"   # unexpected extra indent
    ^
IndentationError: unexpected indent

The body can contain as many statements as needed, though loops that run to more than a few lines are often better refactored into a function:

primes = [2, 3, 5]
for p in primes:
    squared = p ** 2
    cubed = p ** 3
    print(p, squared, cubed)
2 4 8
3 9 27
5 25 125

Iterating over a range of numbers

The built-in range function produces a sequence of integers on demand — it does not build a list in memory, which matters when iterating over millions of values. range(N) yields 0, 1, …, N-1, and range(M, N) yields M, M+1, …, N-1:

for number in range(0, 3):
    print(number)
0
1
2

The accumulator pattern

A common and important programming pattern is to start with an initial value and update it incrementally inside a loop. This is called the accumulator pattern:

total = 0
for number in range(10):
    total = total + (number + 1)
print(total)
55

Read total = total + (number + 1) as: take the current value of total, add number + 1 to it, then store the result back into total. We add 1 because range(10) yields 0 through 9, not 1 through 10. The same pattern works for building up a string, a list, or any other type that can be combined incrementally.

CautionChallenge

Classifying Errors

Is an IndentationError a syntax error or a runtime error?

It is a syntax error. Python detects it while parsing the source code, before any code is executed. A runtime error only appears when the problematic line is actually reached during execution.

CautionChallenge

Tracing Execution

Create a table showing the line numbers and variable values as this program executes:

total = 0
for char in "tin":
    total = total + 1
Line char total
1 0
2 't' 0
3 't' 1
2 'i' 1
3 'i' 2
2 'n' 2
3 'n' 3
CautionChallenge

Reversing a String

Fill in the blanks so that the program prints "nit" (the reverse of "tin"):

original = "tin"
result = ____
for char in original:
    result = ____
print(result)
original = "tin"
result = ""
for char in original:
    result = char + result
print(result)
nit

Each iteration prepends the current character, so the last character ends up first.

CautionChallenge

Practice Accumulating

Fill in the blanks in each program to produce the indicated result.

# Total length of the strings: ["red", "green", "blue"] => 12
total = 0
for word in ["red", "green", "blue"]:
    ____ = ____ + len(word)
print(total)
total = 0
for word in ["red", "green", "blue"]:
    total = total + len(word)
print(total)
12
# List of word lengths: ["red", "green", "blue"] => [3, 5, 4]
lengths = ____
for word in ["red", "green", "blue"]:
    lengths.____(____)
print(lengths)
lengths = []
for word in ["red", "green", "blue"]:
    lengths.append(len(word))
print(lengths)
[3, 5, 4]
# Concatenate all words: ["red", "green", "blue"] => "redgreenblue"
words = ["red", "green", "blue"]
result = ____
for ____ in ____:
    ____
print(result)
words = ["red", "green", "blue"]
result = ""
for word in words:
    result = result + word
print(result)
redgreenblue
# Create acronym: ["red", "green", "blue"] => "RGB"
# write the whole thing
acronym = ""
for word in ["red", "green", "blue"]:
    acronym = acronym + word[0].upper()
print(acronym)
RGB
CautionChallenge

Cumulative Sum

Reorder and properly indent the lines below so that the program prints [1, 3, 5, 10]:

cumulative += [sum]
for number in data:
cumulative = []
sum += number
sum = 0
print(cumulative)
data = [1, 2, 2, 5]
sum = 0
data = [1, 2, 2, 5]
cumulative = []
for number in data:
    sum += number
    cumulative.append(sum)
print(cumulative)
[1, 3, 5, 10]
CautionChallenge

Identifying Variable Name Errors

  1. Read the code below and try to identify the errors without running it.
  2. Run the code and read the error message. Is the NameError caused by a missing quote, a misspelled variable, or a variable that was never defined?
  3. Fix all the errors.
for number in range(10):
    if (Number % 3) == 0:
        message = message + a
    else:
        message = message + "b"
print(message)

There are three errors: Number should be number (Python is case-sensitive), a should be "a" (missing quotes make it a variable reference rather than a string), and message is used before it is defined. The corrected version:

message = ""
for number in range(10):
    if (number % 3) == 0:
        message = message + "a"
    else:
        message = message + "b"
print(message)
abbabbabba
TipKey Points
  • A for loop executes its body once for each item in a collection.
  • The loop header ends with a colon; the body is indented (four spaces by convention).
  • Indentation is always meaningful in Python — unexpected indentation is a syntax error.
  • Use range(N) to iterate over the integers 0 through N-1.
  • The accumulator pattern: initialise a variable before the loop and update it inside.