lua - Lua:如何在键为表(或对象)的表中查找

标签 lua hashtable lua-table

我想存储一个lua表,其中的键是其他lua表。我知道这是可能的,但是我希望能够使用这些表的副本在表中进行查找。具体来说,我希望能够做到:

t = {}
key = { a = "a" }
t[key] = 4
key2 = { a = "a" }

然后我希望能够查找:
t[key2]

并得到4。

我知道我可以将key转换为字符串并将其放入表t中。我还考虑过编写自定义哈希函数或通过嵌套表来实现。我是否有最好的方法来获得这种功能?我还有什么其他选择?

最佳答案

在Lua中,分别创建的两个表被认为是“不同的”。但是,如果一次创建一个表,则可以将其分配给所需的任何变量,并且在比较它们时,Lua会告诉您它们相等。换句话说:

t = {}
key = { a = "a" }
t[key] = 4
key2 = key
...
t[key2] -- returns 4

因此,这就是做您想要的事情的简单,干净的方法。将key存储在某个地方,以便您可以使用它来取回4。这也非常快。

如果您真的不想这样做,那么...有一种方法。但这有点低效和丑陋。

第一部分是制作一个比较两个单独表的函数。如果两个表“相等”,则应返回true,否则返回false。我们称它为等效。它应该像这样工作:
equivalent({a=1},{a=1})          -- true
equivalent({a=1,b=2}, {a=1})     -- false
equivalent({a={b=1}}, {a={b=2}}) -- false

该函数必须是递归的,以处理包含表本身的表。如果其中一个表“包含”另一个表,但具有更多元素,则也不应欺骗它。我想到了这个实现。可能还有更好的选择。
local function equivalent(a,b)
  if type(a) ~= 'table' then return a == b end

  local counta, countb = 0, 0

  for k,va in pairs(a) do
    if not equivalent(va, b[k]) then return false end
    counta = counta + 1
  end

  for _,_ in pairs(b) do countb = countb + 1 end

  return counta == countb
end

我将不在这里解释该功能。我希望它已经足够清楚了。

难题的另一部分在于在比较键时使t使用equivalent函数。这可以通过仔细的元表操作和一个额外的“存储”表来完成。

我们基本上将t转换为冒名顶替者。当我们的代码告诉它在一个键下存储一个值时,它不会将其自身保存;而是将其提供给额外的表(我们将其称为store)。当代码向t询问值时,它将在store中搜索它,但使用equivalent函数来获取它。

这是代码:
local function equivalent(a,b)
... -- same code as before
end

local store = {} -- this is the table that stores the values

t = setmetatable({}, {
  __newindex = store,
  __index = function(tbl, key)
    for k,v in pairs(store) do
      if equivalent(k,key) then return v end
    end
  end
})

用法示例:
t[{a = 1}] = 4

print(t[{a = 1}]) -- 4
print(t[{a = 1, b = 2}]) -- nil

关于lua - Lua:如何在键为表(或对象)的表中查找,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/9201601/

相关文章:

c# - 使用具有公差的 IEqualityComparer GetHashCode

java - 为什么我们需要在哈希表键匹配中进行更多查找?

for-loop - 在for循环中使用整数计数器(i,j,k)来创建表名称/地址时,如何显式调用Lua表值?

Lua - 从嵌套表中获取值

lua - Lua 调用函数

python - 有关获取 aerospike 集中记录总数的说明?是否需要 Lua 脚本?

java - 如何正确实现 Runnable 来搜索哈希表中的元素?

python - 如何在Wireshark中解析protobuf数据包

lua - 协程,Lua中的多个请求

c++ - 从 Visual Studio 构建/运行 Lua