Ms. Nakamura advises the environment club, and once a month she has to report one number: how much paper the club collected. She was doing it with a calculator and a whiteboard, and the whiteboard got wiped once. This program asks for the day’s weights one at a time and gives back the four numbers she actually reports.
The program
# Paper-recycling tally for Ms. Nakamura, who reports one number a
# month and was adding kilograms on a whiteboard.
days = 0
while days < 1:
answer = input("How many collection days are you entering? ")
if answer.isdigit():
days = int(answer)
if days < 1:
print("Please type a whole number of days, like 5.")
total_kilograms = 0.0
heaviest = 0.0
heaviest_day = 0
for day in range(1, days + 1):
kilograms = float(input(f"Day {day} — kilograms collected: "))
total_kilograms = total_kilograms + kilograms
if kilograms > heaviest:
heaviest = kilograms
heaviest_day = day
average = total_kilograms / days
print()
print(f"Collection days: {days}")
print(f"Total collected: {total_kilograms:.1f} kg")
print(f"Average per day: {average:.1f} kg")
print(f"Heaviest day: day {heaviest_day}, {heaviest:.1f} kg")How many collection days are you entering? 4
Day 1 — kilograms collected: 6.5
Day 2 — kilograms collected: 3
Day 3 — kilograms collected: 11.2
Day 4 — kilograms collected: 7
Collection days: 4
Total collected: 27.7 kg
Average per day: 6.9 kg
Heaviest day: day 3, 11.2 kg
How it works
There are two loops, and they are two different kinds on purpose.
The while loop guards the input. Nobody knows how many times somebody
will mistype a number, so the condition is “keep asking while we still
do not have a sensible answer”. answer.isdigit() is True only when
every character typed is a digit, which quietly rejects five, 3.5,
and an empty line without ever raising an error.
The for loop knows its lap count before it starts — days of them —
and does two jobs at once on each pass:
- accumulating:
total_kilogramsstarts at zero and grows by one day’s weight per pass; - remembering the best so far:
heaviestandheaviest_dayupdate together, only when the current day beats the record.
Both patterns depend on their variables being created before the
loop. Move total_kilograms = 0.0 inside the loop and the total resets
every pass, which is the bug traced by hand in
Testing and Debugging.
The last four lines are the whole point of the program. A pile of numbers went in and one report came out — input, process, output, with the process finally doing something worth the trip.
What the guard loop accepts and rejects
How many collection days are you entering? five Please type a whole number of days, like 5. How many collection days are you entering? 0 Please type a whole number of days, like 5. How many collection days are you entering? 3.5 Please type a whole number of days, like 5. How many collection days are you entering? 4 Day 1 — kilograms collected:
0is rejected on purpose: with zero days, the last calculation would betotal_kilograms / 0, and Python would end the program withZeroDivisionError: division by zero. The loop is not politeness — it is the thing standing between the user and a crash.
Change it
- One line. Change
if kilograms > heaviest:to>=. Now, when two days tie for heaviest, the program reports the later one. Neither version is wrong; you just chose, and somebody using this report might care which. - A few lines. Track the lightest day as well, using a second pair
of variables that start from the first day’s weight rather than from
zero. Starting the lightest at
0.0would mean nothing ever beats it — a bug worth making once, on purpose. - A real change. Ms. Nakamura wants to know how many days were
above average. You cannot do it as the program stands, because each
weight is forgotten as soon as it is added — so
appendevery weight to a list, then loop a second time over that list counting the ones aboveaverage. With the run shown above the answer is2. That is exactly the moment Lists stops being an idea and becomes a tool.
Practise the loop patterns in Loops Practice, and see them stated cleanly in Repetition.
Curriculum connection
A2.2
use sequence, selection, and repetition control structures to create programming solutions;
Link to original
A2.3
write algorithms with nested structures (e.g., to count elements in an array, calculate a total, find highest or lowest value, or perform a linear search).
Link to original
B1.3
use the input-process-output model to solve problems.
Link to original