Looping with ipairs

Going through a list from the first item to the last is so common that Lua has a shortcut for it. Besides the numeric for you know, there's a second kind of for loop, which gets its values from a function. With the function ipairs, it goes through the items of a list:

local crops = {"carrot", "potato", "pumpkin"}
for i, crop in ipairs(crops) do
    print(i, crop)
end

This prints:

1	carrot
2	potato
3	pumpkin

Read the first line as: for each index i and item crop in the list crops, do this. In each iteration, the loop gives you two values: the index, and the item at that index. You don't have to write crops[i]: the item is already in crop. The name ipairs comes from index–value pairs.

As in the numeric for, both variables exist only inside the loop, and you can name them as you like. A good name for the item is the singular of the list's name: crop in crops, price in prices.

Often you don't need the index. Then write _ (an underscore) in its place:

local crops = {"carrot", "potato", "pumpkin"}
for _, crop in ipairs(crops) do
    print("Water the " .. crop)
end

This prints:

Water the carrot
Water the potato
Water the pumpkin

_ is an ordinary variable name, but Lua programmers use it for values they don't need, so anyone reading the code knows that the index isn't used. You can't just leave the index out, though. The first variable always gets the index, whatever its name is:

local crops = {"carrot", "potato", "pumpkin"}
for crop in ipairs(crops) do
    print(crop)
end

This prints:

1
2
3

Despite its name, crop got the indexes. Another common mistake is to forget ipairs. The loop expects a function after in, and gets the table instead:

local crops = {"carrot", "potato", "pumpkin"}
for i, crop in crops do
    print(crop)
end
main.lua:2: attempt to call a table value (for iterator 'for iterator')

Two more things to know about ipairs:

  • It stops at the first nil. In a list with a hole, it goes only up to the hole, and skips the items after it. That's another reason not to leave holes.
  • Assigning a new value to crop changes only the variable, not the list. To change an item, write crops[i] = …, as in the previous exercise.

So which loop should you use? ipairs when you go through a list from start to end, which is most of the time. The numeric for when you need something else, such as going backwards. In the lesson on dictionaries, you'll meet the sibling of ipairs, the function pairs.

Instructions

Write a loop with ipairs that goes through eggs, with the variable day for the index and count for the item.

In the loop, print the eggs of each day:

Day 1: 4 eggs
Day 2: 6 eggs
Day 3: 5 eggs
Day 4: 7 eggs
Day 5: 3 eggs
Day 6: 6 eggs
Day 7: 5 eggs

Below it, write a second ipairs loop over eggs, with _ in place of the index. In it, count the good days, when the hens laid at least 6 eggs. (Create the counter before the loop, as in the lesson on loops.)

After the loop, print the result: Good days: 3.

Start programming for free

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

Or sign up with:

6/11