Iterators: point me to some good examples?

Building modules for games those modules invariably contain arrays of objects. Often I need to look through these arrays from other modules. Passing the array back and forth is easy but sloppy and invites errors.

What’s needed is an iterator. Are there any good examples of setting up iterators in Lua? 

I had searched for Lua iterators before, and I always came up with pairs and ipairs which is not really hat I was looking for. After a more careful choice of search terms I found this: http://www.troubleshooters.com/codecorn/lua/luaclosures.htm

That’s a great article. Even though I do some of these already, there were a few tricks in there that I had never thought of.

I had searched for Lua iterators before, and I always came up with pairs and ipairs which is not really hat I was looking for. After a more careful choice of search terms I found this: http://www.troubleshooters.com/codecorn/lua/luaclosures.htm

That’s a great article. Even though I do some of these already, there were a few tricks in there that I had never thought of.

Hi. It looks like this topic has been quiet for a month, so maybe you’re an expert by now, but since it was in the “From the Forum” blog post…

I’ll just throw out some links to code and a little snippet or explanation. If desired, I could probably hunt down some of the actual usage later (where there is any; some of these are either legacy or preparatory).

On the numbers front, you can iterate over the powers of 2 of a number as

local powers = require("bitwise\_ops.powers\_of\_2") for \_, power, bit in powers.PowersOf2(23) do -- = 1 + 2 + 4 + 16 print(power, bit) end -- Results: 16, 4; 4, 2; 2, 1; 1, 0

or iterate over the first n Gray codes (consecutive numbers that only change by one bit):

local gray = require("number\_ops.gray") for num in gray.FirstN(100) do print(num) end

The following iterator behaves like ipairs , but is ignored if the table is nil : IpairsIf

And in that same file, for pairs : PairsIf, which is slightly overloaded to also allow filtering on value type (“table”, “number”, etc.).

Here’s a coroutine-based iterator (used throughout the same file): BlockIter (the non-standard wrap just puts the coroutine body in a loop, whereas it would otherwise be one-shot)

Here’s some iteration over what I’ve called adaptive arrays and adaptive sets (the latter is a misnomer… I’ll rename this to dictionary or map). Basically, these are values that are either nil (unassigned, so far), a non-table (one item assigned), or a table (multiple items assigned), but which can be iterated over without needing to know.

Finally, some stateful iterators (i.e. some information needs to be stored specifically in order to maintain the iterator). This stuff is a little more framework-heavy, being largely built on top of this (which I rambled on about here).

I forget the exact justification of the coroutine one, so I’ll skip that.

The args stuff can be used to iterate varargs (n.b. NOT the arg table, which is deprecated in stock Lua):

local args = require("iterator\_ops.Args") for i, v in args.Args("a", nil, 20, 30, true, false, "BOB") do print(i, v) -- prints 1, "a"; 2, nil; 3, 20; etc. end local function P (...) for i, v in args.Args(...) do print(i, v) -- prints 1, "d"; 2, "p" end end P("d", "p") for i, a, b, c in args.ArgsByN(3, "a", "b", "c", 1, 2, 3, "x", "y", "z" ) do print(i, a, b, c) -- prints 1, "a", "b", "c"; 2, 1, 2, 3; 3, "x", "y", "z" end

The ipairs stuff is motivated by the occasional circumstance where you have some logic that’s shared by an array and a separate item, and it would be more convenient to streamline the use:

local ipairs\_ex = require("iterator\_ops.ipairs") -- Instead of... -- for i, v in ipairs(t) do -- GINORMOUS block of code -- end -- -- Same block of code, mostly repeated for item -- ...do this... for i, v in ipairs\_ex.IpairsThenItem(t, item) do if i then DoArraySpecificThing(t, i) else DoItemSpecificThing(item) end -- Big block of code, just once end ...or this. for i, v in ipairs\_ex.ItemThenIpairs(item, t) do -- Big block end

Too much typing, so I’ll just point out that I also have some iterators for grid-based shapes, over an array-ish class, and over timeouts.

Wow! So much information to digest. Thank you very much for sharing. 

Hi. It looks like this topic has been quiet for a month, so maybe you’re an expert by now, but since it was in the “From the Forum” blog post…

I’ll just throw out some links to code and a little snippet or explanation. If desired, I could probably hunt down some of the actual usage later (where there is any; some of these are either legacy or preparatory).

On the numbers front, you can iterate over the powers of 2 of a number as

local powers = require("bitwise\_ops.powers\_of\_2") for \_, power, bit in powers.PowersOf2(23) do -- = 1 + 2 + 4 + 16 print(power, bit) end -- Results: 16, 4; 4, 2; 2, 1; 1, 0

or iterate over the first n Gray codes (consecutive numbers that only change by one bit):

local gray = require("number\_ops.gray") for num in gray.FirstN(100) do print(num) end

The following iterator behaves like ipairs , but is ignored if the table is nil : IpairsIf

And in that same file, for pairs : PairsIf, which is slightly overloaded to also allow filtering on value type (“table”, “number”, etc.).

Here’s a coroutine-based iterator (used throughout the same file): BlockIter (the non-standard wrap just puts the coroutine body in a loop, whereas it would otherwise be one-shot)

Here’s some iteration over what I’ve called adaptive arrays and adaptive sets (the latter is a misnomer… I’ll rename this to dictionary or map). Basically, these are values that are either nil (unassigned, so far), a non-table (one item assigned), or a table (multiple items assigned), but which can be iterated over without needing to know.

Finally, some stateful iterators (i.e. some information needs to be stored specifically in order to maintain the iterator). This stuff is a little more framework-heavy, being largely built on top of this (which I rambled on about here).

I forget the exact justification of the coroutine one, so I’ll skip that.

The args stuff can be used to iterate varargs (n.b. NOT the arg table, which is deprecated in stock Lua):

local args = require("iterator\_ops.Args") for i, v in args.Args("a", nil, 20, 30, true, false, "BOB") do print(i, v) -- prints 1, "a"; 2, nil; 3, 20; etc. end local function P (...) for i, v in args.Args(...) do print(i, v) -- prints 1, "d"; 2, "p" end end P("d", "p") for i, a, b, c in args.ArgsByN(3, "a", "b", "c", 1, 2, 3, "x", "y", "z" ) do print(i, a, b, c) -- prints 1, "a", "b", "c"; 2, 1, 2, 3; 3, "x", "y", "z" end

The ipairs stuff is motivated by the occasional circumstance where you have some logic that’s shared by an array and a separate item, and it would be more convenient to streamline the use:

local ipairs\_ex = require("iterator\_ops.ipairs") -- Instead of... -- for i, v in ipairs(t) do -- GINORMOUS block of code -- end -- -- Same block of code, mostly repeated for item -- ...do this... for i, v in ipairs\_ex.IpairsThenItem(t, item) do if i then DoArraySpecificThing(t, i) else DoItemSpecificThing(item) end -- Big block of code, just once end ...or this. for i, v in ipairs\_ex.ItemThenIpairs(item, t) do -- Big block end

Too much typing, so I’ll just point out that I also have some iterators for grid-based shapes, over an array-ish class, and over timeouts.

Wow! So much information to digest. Thank you very much for sharing.