lua-users home
lua-l archive

[Date Prev][Date Next][Thread Prev][Thread Next] [Date Index] [Thread Index]


On Sat, Sep 26, 2020 at 9:50 PM Eretnek Hippi Messiás
<hippi777@protonmail.com> wrote:
> 2nd:
> make a `table.new()` (or anything like) that prefills ur table with these `NULL`s for the keys u want (with a hash part that has unknown keys, it is harder, but when they are known, then this initializer can get the keys). and give it a metatable where `__newindex` will insert a `NULL` instead of `nil`s and where `__index` will give back `nil`s instead of `NULL`s.
>
It is not necessary to use a NULL or a metatable, because values that
are set to some non-nil value then set to nil keep their entries in
the table. That is, the entry is not deleted by setting it to nil, it
would only be deleted in a rehash. This is why you can delete some
keys from a table while iterating over it.

So if you know your key set, it is sufficient to initialize your table
like this:

local all_keys = {"x", "y", "cow", "chicken", "duck"}
local function table_new()
  local t = {}
  for _,k in ipairs(all_keys) do
    t[k] = true
  end
  for _,k in ipairs(all_keys) do
    t[k] = nil
  end
  return t
end

> probably some implementation details could matter a bit (like the actual size could vary, while still being constant), but if either u dont change the number of the elements in the hash part or u dont cross a boundary for the size (to trigger a shrink/grow), then it shouldnt change. the former is more questionable if theres a way at all for removing and adding a key, in other words, change one to something else, either to consume a dummy placeholder or just to reuse a key slot...
In the implementation we have, if the key set changes over time, you
will trigger a rehash, even if you do not increase the size of the
table.