You're grading 30 student exams. Instead of writing the same calculation 30 times, you use a loop: for each exam, calculate the percentage, record the grade. Same logic, applied to every item in your list.

Print each element

Visit every element in a list, one by one.

print_all.py
Replay: real traced execution (multi-file project)
nums = [10, 20, 30, 40, 50]

print("nums=" + str(nums))
for i in range(len(nums)):
    x = nums[i]
  1. nums ← [10, 20, 30, 40, 50]

    1nums→ [10, 20, 30, 40, 50] = [10, 20, 30, 40, 50]23print("nums=" + str(nums[10, 20, 30, 40, 50]))4for i in range(len(nums)):
    outputnums=[10, 20, 30, 40, 50]
  2. x ← 10

    pass 1 of 5
    3print("nums=" + str(nums))4for i0 in range(len(nums[10, 20, 30, 40, 50])):5    x→ 10 = nums[i]10
    All 5 passes — pass 1 is the card above
    passinums[i]x
    101010
    212020
    323030
    434040
    545050

The loop runs once for each element. i is the index: 0, 1, 2, 3, 4.

for `for i in range(n)` - runs n times, i goes from 0 to n-1.
range `range(n)` gives numbers 0, 1, 2, ..., n-1.

Sum of a list

Add up all the numbers in a list.

sum.py
Replay: real traced execution (multi-file project)
nums = [10, 20, 30, 40, 50]

print("nums=" + str(nums))
sum = 0

for i in range(len(nums)):
    sum = sum + nums[i]

  1. nums ← [10, 20, 30, 40, 50], sum ← 0

    1nums→ [10, 20, 30, 40, 50] = [10, 20, 30, 40, 50]23print("nums=" + str(nums[10, 20, 30, 40, 50]))4sum→ 0 = 05#?accumulator
    outputnums=[10, 20, 30, 40, 50]
  2. sum ← 10

    pass 1 of 5
    5#?accumulator6for i0 in range(len(nums[10, 20, 30, 40, 50])):7    sum→ 10 = sum + nums[i]10
    All 5 passes — pass 1 is the card above
    passinums[i]sum
    10100 10
    212010 30
    323030 60
    434060 100
    5450100 150

Start with total = 0, then add each element one by one. This pattern is called an accumulator.

See the Loop State

A loop is easier to trust when you can see the variable state after each pass. These diagrams use the exact nums = [10, 20, 30, 40, 50] sum example above.

Accumulator state for sum.pyAccumulator state for sum.pystepinums[i]sum afterstart--010101021203032306043401005450150
The accumulator starts at 0. After each iteration, `sum` holds the total of the values already visited.
Accumulator updates in orderAccumulator updates in ordersum=0+10 -> 10+20 -> 30+30 -> 60+40 -> 100+50 -> 150
The same update rule repeats: take the old `sum`, add the current list value, store the new `sum`.

Count how many elements match

How many numbers are greater than 50?

count.py
Replay: real traced execution (multi-file project)
nums = [35, 72, 48, 91, 56, 23, 88]

print("nums=" + str(nums))
count = 0
for i in range(len(nums)):
    if nums[i] > 50:
        count = count + 1
  1. nums ← [35, 72, 48, 91, 56, 23, 88], count ← 0

    1nums→ [35, 72, 48, 91, 56, 23, 88] = [35, 72, 48, 91, 56, 23, 88]23print("nums=" + str(nums[35, 72, 48, 91, 56, 23, 88]))4count→ 0 = 05for i in range(len(nums)):
    outputnums=[35, 72, 48, 91, 56, 23, 88]
  2. for i in range(len(nums)):

    pass 1 of 7
    4count = 05for i0 in range(len(nums[35, 72, 48, 91, 56, 23, 88])):6    if nums[i] > 50:7        count = count + 1
    All 7 passes — pass 1 is the card above
    passi
    10
    21
    32
    43
    54
    65
    76
  3. count ← 1

    pass 1 of 4
    5for i in range(len(nums)):6    if nums[i]72 > 50:7        count→ 1 = count + 1
    All 4 passes — pass 1 is the card above
    passnums[i]count
    1720 1
    2911 2
    3562 3
    4883 4

Use a counter variable, increment it when condition is met.

Fibonacci with a loop

Generate Fibonacci numbers using a loop instead of writing each line.

n
fibonacci.py
Replay: real traced execution (multi-file project)
n = 10
fib = [0] * n

fib[0] = 0
fib[1] = 1

for i in range(2, n):
    fib[i] = fib[i - 1] + fib[i - 2]

print("fib=" + str(fib))
n = 5
fib = [0] * n

fib[0] = 0
fib[1] = 1

for i in range(2, n):
    fib[i] = fib[i - 1] + fib[i - 2]

print("fib=" + str(fib))
n = 15
fib = [0] * n

fib[0] = 0
fib[1] = 1

for i in range(2, n):
    fib[i] = fib[i - 1] + fib[i - 2]

print("fib=" + str(fib))
  1. n ← 10, fib ← [0, 0, 0, 0, 0, 0, 0, 0, 0, 0], fib[0] ← 0, fib[1] ← 1

    1n→ 10 = 10  #@n=5, 152fib→ [0, 0, 0, 0, 0, 0, 0, 0, 0, 0] = [0] * n1034fib[0]→ 0 = 05fib[1]→ 1 = 1
  2. fib[i] ← 1

    pass 1 of 8
    7for i2 in range(2, n10):8    fib[i]→ 1 = fib[i - 1]1 + fib[i - 2]0
    All 8 passes — pass 1 is the card above
    passifib[i - 1]fib[i - 2]fib[i]
    12101
    23112
    34213
    45325
    56538
    678513
    7813821
    89211334
  3. print("fib=" + str(fib))

    10print("fib=" + str(fib[0, 1, 1, 2, 3, 5, 8, 13, 21, 34]))
    outputfib=[0, 1, 1, 2, 3, 5, 8, 13, 21, 34]
  1. n ← 5, fib ← [0, 0, 0, 0, 0], fib[0] ← 0, fib[1] ← 1

    1n→ 5 = 52fib→ [0, 0, 0, 0, 0] = [0] * n534fib[0]→ 0 = 05fib[1]→ 1 = 1
  2. fib[i] ← 1

    pass 1 of 3
    7for i2 in range(2, n5):8    fib[i]→ 1 = fib[i - 1]1 + fib[i - 2]0
    All 3 passes — pass 1 is the card above
    passifib[i - 1]fib[i - 2]fib[i]
    12101
    23112
    34213
  3. print("fib=" + str(fib))

    10print("fib=" + str(fib[0, 1, 1, 2, 3]))
    outputfib=[0, 1, 1, 2, 3]
  1. n ← 15, fib ← [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0], fib[0] ← 0

    1n→ 15 = 152fib→ [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0] = [0] * n1534fib[0]→ 0 = 05fib[1]→ 1 = 1
  2. fib[i] ← 1

    pass 1 of 13
    7for i2 in range(2, n15):8    fib[i]→ 1 = fib[i - 1]1 + fib[i - 2]0
    13 passes — pass 1 is the card above
    passifib[i - 1]fib[i - 2]fib[i]
    12101
    23112
    34213
    45325
    56538
    678513
    7813821
    89211334
    910342155
    ⋯ 2 more passes ⋯
    121314489233
    1314233144377
  3. print("fib=" + str(fib))

    10print("fib=" + str(fib[0, 1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89, 144, 233, 377]))
    outputfib=[0, 1, 1, 2, 3, 5, 8, 13, 21, 34, 55, 89, 144, 233, 377]

The loop pattern: each element depends on the previous two. Loops let us express this once, then repeat it as many times as needed.

while `while condition:` - another way to loop, checks condition before each iteration.