Reputation: 133
I have two set of values defined:
local A1 = {100, 200, 300, 400}
local A2 = {500, 600, 700, 800}
I want to iterate a loop assigning values for another variable B1 and B2 as pairs from A1 and A2 as follows:
B1 = 100 and B2 = 500 (first iteration)
B1 =200 and B2 = 600 (second iteration)
B1 = 300 and B2 = 700 (third iteration)
B1=400 and B2 = 800 (fourth iteration)
I tried to use ipairs as follows:
for i, f1 in ipairs(A1) do
for j, f2 in ipairs(A2) do
B1 = f1
B2 = f2
end
end
but this gave me
B1 = 100 and B2 = 500 (first iteration)
B1 =100 and B2 = 600 (second iteration)
B1 = 100 and B2 = 700 (third iteration)
B1=100 and B2 = 800 (fourth iteration)
B1 = 200 and B2 = 500 (fifth iteration)
B1 =200 and B2 = 600 (sixth iteration)
B1 =200 and B2 = 700 (seventh iteration)
....
...
...
so on...
can anyone help me to code in the right way?
Upvotes: 2
Views: 1150
Reputation: 186
The previous answers are more detailed and provide a more general and better answer.
This one is for someone very new to Lua. Not only does it show two loops, it reinforces that there is usually more than one way to get where you want to go.
local A1 = {100, 200, 300, 400}
local A2 = {500, 600, 700, 800}
print("simplest answer:")
-- doesn't use ipairs and assumes A1 and A2 are the same size
for i = 1, #A1 do
B1 = A1[i]
B2 = A2[i]
print(B1, B2, "(iteration #"..i..")")
end
print()
print("answer that uses ipairs:")
-- again, assumes A1 and A2 are the same size
for i, v in ipairs(A1) do
B1 = A1[i] -- i steps through A1 and A2
B2 = A2[i] -- this works because A1 and A2 are same size
print(B1, B2, "(iteration #"..i..")")
end
Gives this output:
simplest answer:
100 500 (iteration #1)
200 600 (iteration #2)
300 700 (iteration #3)
400 800 (iteration #4)
answer that uses ipairs:
100 500 (iteration #1)
200 600 (iteration #2)
300 700 (iteration #3)
400 800 (iteration #4)
Upvotes: 0
Reputation: 5751
You can build on the ipairs
example from Programming in Lua. For instance this version iterates over 2 sequences in parallel:
-- iterator function
local function iter_ipairs2(tablePair, i)
i = i + 1
local v1 = tablePair[1][i]
local v2 = tablePair[2][i]
-- if you use 'and' here the iteration stops after finishing
-- the shortest sequence. If you use 'or' the iteration
-- will stop after it finishes the longest sequence.
if v1 and v2 then
return i, v1, v2
end
end
-- this is the function you'll call from your other code:
local function ipairs2(t1, t2)
return iter_ipairs2, {t1, t2}, 0
end
-- usage:
local A1 = {100, 200, 300, 400, 500}
local A2 = {500, 600, 700, 800}
for i, v1, v2 in ipairs2(A1, A2) do
print(i, v1, v2)
end
Upvotes: 1
Reputation: 26355
You can easily do this with a numerical loop:
for i = 1, 4 do
local a, b = A1[i], B1[i]
--- use them
end
How you go about determining the number of iterations you'll need is the tricky part. If the sizes are variant, but each table is the same length as the others you can instead use the length operator (#A1
).
Alternatively, you might want a function that returns the largest length of a given set of tables.
local function max_table_len (...)
local tabs = { ... }
local len = 0
for i = 1, #tabs do
local l = #tabs[i]
if l > len then
len = l
end
end
return len
end
And maybe even a helper function to get each value.
local function get_from_tables (index, ...)
local values = { ... }
local len = #values
for i = 1, len do
values[i] = values[i][index]
end
return table.unpack(values, 1, len)
end
Ending up with something like:
for index = 1, max_table_len(A1, B1) do
local a, b = get_from_tables(index, A1, B1)
end
Upvotes: 3