Loop patterns
Running totals, counting, finding the largest, nested loops and trace tables.
Do this lesson in the simulatorMost loops you will ever write follow one of a handful of patterns. Learn to spot them and a new problem often turns out to be an old one: a running total, a count, the biggest so far, or a loop inside a loop.
Running total
Start a variable at 0 before the loop, and add to it each time round:
# the two lines every program starts with: the commands, then the robot
from bugbot import *
connect()
total = 0
for i in range(5):
d = distance()
print("reading", i + 1, "is", d)
total = total + d
forward(50, distance=5)
print("total", total)
print("average", total / 5)
The total must start before the loop. Put total = 0 inside the loop and it is wiped every time round. Dividing the total by how many readings there were gives the average.
Counting
A count is a running total that adds 1 when something is true:
# the two lines every program starts with: the commands, then the robot
from bugbot import *
connect()
close = 0
for i in range(8):
if distance() < 40:
close = close + 1
turn_right(30, angle=45)
print("things closer than 40 cm in", close, "of 8 directions")
The robot looks in eight directions, 45 degrees apart, and counts how many are crowded. The if decides whether this time round counts.
Finding the largest
Keep the best value so far, and replace it whenever you find a better one:
# the two lines every program starts with: the commands, then the robot
from bugbot import *
connect()
most = 0
best = 0
for i in range(8):
d = distance()
if d > most:
most = d
best = i * 45
turn_right(30, angle=45)
print("most room:", most, "cm at", best, "degrees")
turn_right(30, angle=best)
forward(50, distance=most / 2)
Two variables travel together: most remembers the largest distance, and best remembers where it was. At the end the robot turns to face the most room and drives half way into it. Starting most at 0 works because every distance is bigger than 0; for the smallest, start with a very large number instead.
Loops inside loops
A loop's block can hold another loop. The inner loop runs all the way through, every time the outer loop goes round once:
# the two lines every program starts with: the commands, then the robot
from bugbot import *
connect()
for row in range(1, 4):
for col in range(1, 5):
print(row * col, end=" ")
print()
end=" " makes print finish with a space instead of a new line, so each row stays on one line, and the bare print() ends the row. The outer loop runs 3 times, the inner loop 4 times for each of those: 12 numbers in all.
With the robot, nested loops draw shapes made of shapes:
# the two lines every program starts with: the commands, then the robot
from bugbot import *
connect()
for square in range(2):
for side in range(4):
forward(60, distance=20)
turn_right(30, angle=90)
tone(660, 0.2)
right(60, distance=25)
Tracing a loop
Follow a loop by hand with a trace table: one column per variable, one row per time round. Here is the running total from the start of this lesson, with made-up readings of 40, 35, 30:
| i | d | total |
|---|---|---|
| 0 | ||
| 0 | 40 | 40 |
| 1 | 35 | 75 |
| 2 | 30 | 105 |
Tracing is how you find logic errors in loops without a computer, and it is how exams test that you understand them.
Task: times grid
Print a multiplication grid of five rows and five columns with two nested for loops. Each row is the numbers separated by single spaces, so the first row is 1 2 3 4 5 and the last is 5 10 15 20 25. Work the numbers out; do not type them. The robot must not drive.
# the two lines every program starts with: the commands, then the robot
from bugbot import *
connect()
for row in range(1, 6):
print(row)
Task: most room
The robot is boxed in on three sides. Look in four directions, 90 degrees apart, and find the one with the most room. Print most room at <degrees>, using 0, 90, 180 or 270, then turn to face that way.
# the two lines every program starts with: the commands, then the robot
from bugbot import *
connect()
most = 0
best = 0
for i in range(4):
d = distance()
turn_right(30, angle=90)
Challenges
- Find the smallest distance in eight directions, and which way it is.
- Print a triangle of stars with nested loops: one star on the first row, two on the second, up to five.
- Take ten distance readings while driving and print how many were under 30, and their average.