Loops, and where your data lives

INPUT · Slides

Holding it in dictionaries instead

01 / 07

By number, or by name

With two containers to choose from it is not always obvious which to reach for. The rule of thumb is this.

  • Several of the same kind of thing in a row — a list. "Five scores", "three fruits"
  • The parts that make up one thing — a dictionary. "A name, a price and a count"

Last lesson the names, prices and counts sat in three separate lists. That was one record pulled apart and forced to live in pieces.

02 / 07

Make one record a dictionary

Turn a single record into a dictionary and the name and the price stop drifting apart. There is no numbering to keep in step either.

To take something out, write the key inside the []. It is a name rather than a number, so the order does not matter.

item = {"name": "bread", "price": 160}print(item["name"])print(item["price"])

Result

bread
160

03 / 07

Line the dictionaries up in a list

Then line those dictionaries up in a list. This is the most ordinary shape real data comes in. A register, a product list, a history of orders — nearly all of it looks like this.

Put a loop round it and the same code handles three records or a thousand. This is where the chapter has been heading.

basket = [{"name": "bread", "price": 160}, {"name": "jam", "price": 220}]for item in basket:    print(item["name"])

Result

bread
jam

04 / 07

Take one value into a variable

Writing item["name"] over and over gets hard to read. Give the value you took out a name and it reads far better.

Inside an f-string especially, {item["name"]} doubles the quotes up and is awkward to write. Take it into a variable first and that worry disappears.

item = {"name": "bread", "price": 160, "count": 2}name = item["name"]subtotal = item["price"] * item["count"]print(f"{name} ${subtotal}")

Result

bread $320

05 / 07

A field that might not be there

Look up a key that is not in the dictionary with [] and you get a KeyError and everything stops. When you are not sure it is there, use in or get.

  • if "stock" in item: … ask whether it is there
  • item.get("stock", 0) … get 0 back when it is not

Real data has gaps in it. Writing code that does not stop when a field is missing is worth a lot.

item = {"name": "jam"}print(item.get("stock", 0))

Result

0

06 / 07

To count things, pile up into a dictionary

When you want to know "how many of each", put an empty dictionary outside the loop and add into it as you go.

A key you are seeing for the first time is not in the dictionary yet, so check with in and put 1 in. From the second time on, += 1. This shape is worth learning by heart exactly as it stands.

fruits = ["apple", "orange", "apple"]counts = {}for fruit in fruits:    if fruit in counts:        counts[fruit] += 1    else:        counts[fruit] = 1print(counts)

Result

{'apple': 2, 'orange': 1}

07 / 07

From here on, make parts

With containers and loops in hand you can write most kinds of data handling. What is left is the business of not writing the same thing twice.

Next chapter you give a piece of work a name so that you can call on it. The totalling you wrote here gets a name too, and becomes a part you can use whenever you like.

Before that, ten questions to finish on.