how to delete all elements in a Lua table?

55,070

Solution 1

for k in pairs (t) do
    t [k] = nil
end

Will also work - you may have difficulty with ipairs if the table isn't used as an array throughout.

Solution 2

Table elements insert and remove performance compare

The Table size count 10000000

[1] while and rawset

while #t ~= 0 do rawset(t, #t, nil) end

spent time = 0.677220

[2] next and rawset

for k in next, t do rawset(t, k, nil) end

spent time = 0.344533

[3] ipairs and rawset

for i, v in ipairs(t) do t[i] = nil end

spent time = 0.012450

[4] for, rawset

count = #t
for i=0, count do t[i]=nil end

spent time = 0.009308

Table elemnets insert

[1] table insert function

for i=0, 10000000 do    table.insert(t, i, i) end

spent time = 1.0590489

[2] use #t

for i=0, 10000000 do    t[#t+1] = i end

spent time = 0.703731

[3] for, rawset

for i=0, 10000000 do rawset(t, i, i) end

spent time = 0.100010

result.

Fastest remove : 4

Fastest insert : 3

Solution 3

easiest and most performant:

for k,v in pairs(tab) do tab[k]=nil end

What you suggest isn't usable: table.remove shifts the remaining elements to close the hole, and thus messes up the table traversal. See the description for the next function for more info

Solution 4

For a faster version that ignores the __pairs metamethod:

local next = next
local k = next(tab)
while k ~= nil do
  tab[k] = nil
  k = next(tab, k)
end

EDIT: As @siffiejoe mentions in the comments, this can be simplified back into a for loop by replacing the pairs call with its default return value for tables: the next method and the table itself. Additionally, to avoid all metamethods, use the rawset method for table index assignment:

for k in next, tab do rawset(tab, k, nil) end

Solution 5

#table is the table size and so if t = {1,2,3} then #t = 3

So you can use this code to remove the elements

while #t ~= 0 do rawset(t, #t, nil) end

You will go through the table and remove each element and you get an empty table in the end.

Share:
55,070

Related videos on Youtube

bob
Author by

bob

Updated on July 09, 2022

Comments

  • bob
    bob almost 2 years

    How do I delete all elements inside a Lua table? I don't want to do:

    t = {}
    table.insert(t, 1)
    t = {}  -- this assigns a new pointer to t
    

    I want to retain the same pointer to t, but delete all elements within t.

    I tried:

    t = {}
    table.insert(t, 1)
    for i,v in ipairs(t) do table.remove(t, i) end
    

    Is the above valid? Or is something else needed?

    • AndersH
      AndersH about 13 years
      I guess the situation is to empty a table in a function taking it as a parameter. Then the question is a good one, +1. I was at first confused about the word "pointer", which exists in c-code and shouldn't be mentioned in Lua-code. You mean "reference" or something.
  • siffiejoe
    siffiejoe over 9 years
    Or just for k in next,tab do tab[k] = nil end
  • Klaatu von Schlacker
    Klaatu von Schlacker over 5 years
    This is a thorough and effective answer.
  • Danger Code master
    Danger Code master over 5 years
    According to lua.org/gems/sample.pdf (a Lua optimization guide), this method is surprisingly terrible. The problem is that setting an element to nil typically does not delete it from the table until the next resize. The implementation of next has to search through all the nils before it returns, making this a surprise O(n^2).
  • bonsaiviking
    bonsaiviking over 5 years
    @AHelps Thanks for pointing that out! My longer while version doesn't suffer from this because next is called with a previous index. @siffiejoe's version is missing that part, so it does the slow version. I'll make an explanatory edit to the answer.
  • bonsaiviking
    bonsaiviking over 5 years
    @AHelps actually, I take that back: the "generic for loop" construct automatically takes the return value of the iterator function as the second parameter to the function in the next iteration. So first iteration is k = next(tab, nil), but the next iteration is k = next(tab, k), which avoids the full traversal.