【问题标题】:Difference between two tables as a table两张表作为一张表的区别
【发布时间】:2019-12-14 17:10:37
【问题描述】:

简短

t1 = {1,3,5,7,9}

t2 = {1,2,3,4,5,6,7,8,9}

想要的结果:t3 = {2,4,6,8}

详细说明

我有一个场景中的对象列表,并且我有一个不在场景中的所有对象的列表。我正在尝试编写一段简单的代码,允许我将对象添加到场景中,但要确保它不会加载已经加载的对象。

所以我可以这样说......

SafeAdd (2, currentOBJlist, notLoadedOBJList)

并让应用程序从“notLoadedOBJList”中加载 2 个随机对象,但所选对象不在“currentOBJlist”中

【问题讨论】:

  • 两个序列t1t2都保证被排序吗?性能是个问题吗?
  • 如果这些列表实际上是,请将它们创建为{ [1]=true, [3]=true, ...}。然后决定一个集合的一个元素是否在另一个集合中需要恒定的时间。

标签: lua set-difference


【解决方案1】:

未排序的数组

Lua 中的表除了是数组/列表之外,也是一个 map/dictionary/set

通过将true 分配给列表中的每个元素来创建一个集合;这样,您可以通过查找密钥来将其用作一组。如果返回的键是nil,那么它不存在,否则它会返回true

function notInScene(allObjects, objectsInScene)
  -- build a set out of objectsInScene
  -- this step can be avoided, if it's already a set
  local set = {}
  for _, v in ipairs(objectsInScene) do
    set[v] = true
  end

  -- populate output
  local notPresent = { }
  for _, v in ipairs(allObjects) do
    if (set[v] == nil) then
      table.insert(notPresent, v)
    end
  end
  return notPresent
end

local t1 = {1,3,5,7,9}
local t2 = {1,2,3,4,5,6,7,8,9}
local t3 = notPresent(t2, t1)
for _, v in ipairs(t3) do print(v) end

输出

2
4
6
8

请注意,我们将 objectsInScene 复制为一个集合;如果可能的话,应该避免这种情况,即在最初构建时将 objectsInScene 设置为一个集合。

排序数组

如果保证两个列表都被排序,我们可以做得比构建一个集合然后查找它要好得多——这是一个两遍的解决方案,效率不高。

function notInScene(allObjects, objectsInScene)
  j = 1
  local notPresent = {}
  for i = 1, #allObjects do
    if (allObjects[i] == objectsInScene[j]) then
      j = j + 1
    elseif (allObjects[i] < objectsInScene[j]) then
      table.insert(notPresent, allObjects[i])
    end
    i = i + 1
  end
  return notPresent
end

这会产生相同的结果,但不会花费额外的空间或时间;它比以前的方法更可取。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2019-11-15
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多