Counting with a Table

Dictionaries are great for counting. Emma has written down the weather of each day this week, and she wants to know how many days were sunny, rainy and cloudy. Make a dictionary whose keys are the kinds of weather and whose values are the numbers of days. Start with an empty table and go through the list; for each day, add 1 to the number of its weather:

local weather = {"sunny", "rainy", "sunny", "cloudy", "sunny", "rainy", "sunny"}

local days = {}
for _, w in ipairs(weather) do
    days[w] = (days[w] or 0) + 1
end

print("Sunny: " .. days.sunny)
print("Rainy: " .. days.rainy)
print("Cloudy: " .. days.cloudy)

This prints:

Sunny: 4
Rainy: 2
Cloudy: 1

The important line is days[w] = (days[w] or 0) + 1. Follow it through the first three days:

  • On the first day, w is "sunny". There's no key sunny yet, so days[w] is nil, nil or 0 is 0, and days.sunny becomes 1.
  • On the second day, w is "rainy", which isn't there either: days.rainy becomes 1.
  • On the third day, it's "sunny" again. Now days[w] is 1, 1 or 0 is 1, and days.sunny becomes 2.

You don't need to know in advance which kinds of weather there are. A new one gets its own key the first time it appears.

Two typical mistakes:

  • Without or 0: days[w] = days[w] + 1 ends on the first day with attempt to perform arithmetic on a nil value (field '?'), because there's no number to add 1 to yet.
  • Without the parentheses: days[w] = days[w] or 0 + 1. There's no error, but + goes before or, so Lua computes days[w] or 1, and every kind of weather stays at 1.

The same pattern adds up amounts instead of counting: totals[crop] = (totals[crop] or 0) + amount.

To find what was most common, go through the counts with pairs and use the pattern for the largest value from the lesson on lists. Here the order of pairs doesn't matter: whatever the order, the largest number is the same:

local days = {sunny = 4, rainy = 2, cloudy = 1}

local best = nil
local bestCount = 0
for w, count in pairs(days) do
    if count > bestCount then
        best = w
        bestCount = count
    end
end
print("Most days: " .. best .. " (" .. bestCount .. ")")

This prints:

Most days: sunny (4)

In the lesson on lists, you started the search with the first item. A dictionary has no first item, but a count is never less than 1, so here it's safe to start with 0. And only if two kinds of weather had the same largest number would the order decide which of them is printed.

Instructions

Count how many pieces of each crop Emma sold: create an empty table counts and fill it in a loop over sold. Then print the counts of carrots and strawberries from it:

Carrots: 4
Strawberries: 3

Below, find the crop that sold best: go through counts with pairs and keep the largest count. Print:

Best seller: carrot (4)

Start programming for free

By signing up, you agree to the Terms of Service and Privacy Policy.

Or sign up with:

5/10