【问题标题】:insert table values with string keys into Lua table将带有字符串键的表值插入 Lua 表
【发布时间】:2014-05-01 03:22:30
【问题描述】:

我对 Lua 语言比较陌生,而且我显然缺少关于表结构的一些东西。

我正在尝试创建一个表,表中的每个表都有一个键,值是相应的表。

好的,这句话可能会令人困惑。这是一个例子:

{{ key = "RC", value = {1, 2, 3, 4}},
 { key = "M",  value = {4, 8, 7}},
 { key = "D",  value = {3, 8, 9}}
 ...}

为此,我使用了以下算法:

local listOfLists = {};
...
if condition1 then
   listOfLists[key1] = list1;
end
...
if condition2 then
   listOfLists[key2] = list2;
end
...

等等……

我希望稍后使用这些键来确定哪些列表已添加到表中。 但问题是,即使满足所有条件,似乎也没有列表添加到表中。

我可以使用table.insert(listOfLists, list1) 代替listOfLists[key1] = list1,但我无法分辨哪些列表已添加到集合中。 蚂蚁建议?

【问题讨论】:

  • 请注意,您提供的示例满足listOfLists[key1] = list1key1 整数和list1 形式的{key="R", value={1,2,3,..}}。根据您的要求,更实用的结构可能是{ RC = {1,2,3,...}, M = {4,8,7}, ... },即其中key1 是原始list1 的键,list1 是值表。当条件1满足时,你能打印出key1list1是什么吗?做print("key", type(key1), key1, "list", type(list1), list1).
  • 为了清楚起见,我明确指出了“键”和“值”,但似乎我反而增加了混淆。我正在尝试构建的正是您在评论{ RC = {1,2,3,...}, M = {4,8,7}, ... } 中描述的内容,但没有成功。
  • 好的,那么我怀疑你得到的答案是否有助于解决“即使满足所有条件也不会将列表添加到表中”,到目前为止的状态是什么?如果没有,我认为您将不得不发布更详细的代码来显示您拥有的结构、实际情况以及将项目添加到列表中,因为您所显示的内容看起来很好,所以问题出在未显示的代码中。跨度>

标签: lua lua-table


【解决方案1】:

Lua 表是一种灵活的数据结构。元素是键值对。键是除nil 之外的任何Lua 值。一个值可以是除nil 之外的任何值。将 nil 分配给该值会消除该对。

具有number 类型的键值(从 1 到 n 的整数)的表(可能为空)子集称为序列。 n 被确定为与nil 值配对的最后一个此类键。几个表函数和运算符仅适用于序列。

表构造函数允许键的几种语法:

  1. 通过序列暗示:{1, 2, 3}
  2. 显式键:{[1] = 1, [3] = 3, ["two"] = "value"}
  3. 标识符键:{one = 1, two = 2}

表构造函数可以使用它们的任意组合。

您已经定义了一个元素序列,每个元素都是一个包含两个元素的表格, 第二个是一个序列。

看来您希望键是字符串,值是序列:

{ 
  RC = {1, 2, 3, 4},
  M = {4, 8, 7},
  D = {3, 8, 9}
}

【讨论】:

  • 谢谢汤姆,你解释得比我清楚得多。这就是我想要的,但不幸的是我无法实现。根据我在 Lua.org 上阅读的内容,我预计 local listOfLists = {};listOfLists["RC"] = {1, 2, 3, 4}; 会生成类似 { RC = {1, 2, 3, 4}} 的内容,但操作后 listOfLists 表仍然是 {}。 table.maxn(listOfLists)返回0
  • maxn 在这种情况下应该返回 0,因为您没有任何 number 类型的正整数键。唯一的键是字符串“RC”。试试table.maxn(listOfLists.RC);应该是 4。
【解决方案2】:

很难理解,你想要实现什么。因此,如果您想要更具体的答案,请提供更多信息。

您可以创建表的关联表。

local map = {}
map["key"] = { 1, 2, 3, 4 }
print(map.key[3])

或者你可以创建一个表数组

local vector = {}
vector[1] = { 1, 2, 3, 4 }
print(vector[1][2])

或者你可以结合方法。

创建

{{ key = "RC", value = {1, 2, 3, 4}},
{ key = "M",  value = {4, 8, 7}},
{ key = "D",  value = {3, 8, 9}}
...}

您可以使用table constructor 或代码中的smth。

local tbl = { { key = "RC", value = {1, 2, 3, 4}} } -- init first elem from constructor
table.insert(tbl, { key = "M", value = {4, 8, 7}}) -- table insert & constructor
tbl[2] = {} -- Array-based access.
tbl[2].key = "D" --key access
tbl[2]["value"] = { 3, 8, 9 } -- other way

请注意,每个表由两部分组成:从 1 到 N 的顺序键的向量,以及其他部分的映射。某些函数,例如表长度运算符或 ipairs 迭代器,保证仅适用于表的向量部分。但它们的速度明显更快。

编辑:(最后一段解释)

如果您有一个包含一些键的表并且想要迭代,您可以使用 ipairs 或pairs。

ipairs 是有序的,从 1 到第一个非零元素。它不会迭代非整数键。 pairs 可以通过任何键,但不保证顺序。

local map = { 1, 2, 3, key = 6, [5] = 5 }
for i, v in ipairs(map) do
  print(v) -- will output 1, 2, 3. first nil element is map[4]. map[5] will mot be visited.
end

for i, v in pairs(map) do -- NOTE pairs usage
  print(v) -- will output 1, 2, 3, 5, 6 in ANY order
end

map[4] = 4 -- Fill gap
for i, v in ipairs(map) do
   print(v) -- will output 1, 2, 3, 4, 5. Now first nil element is map[6]
end

长度运算符的作用类似于ipairs,它不计算未被ipairs 方法访问的元素。

table.maxn 与 数字索引 一起使用,并且将为您的表格返回零。 参考说table.maxn

返回给定表的最大正数字索引,如果表没有正数字索引,则返回零。 (为了完成它的工作,这个函数会线性遍历整个表。)

关于长度和table.maxn的小例子

local a = { 1, 2, 3, [5] = 5}
print(table.maxn(a)) -- 5
print(#a) -- 3
a = { key = 4 } 
print(table.maxn(a)) -- 0
print(#a) -- 0
print(a["key"]) -- 4, nothing is lost
local num = 0
for _, __ in pairs(a) do num = num + 1 end
print(num) -- 1 We find it.

【讨论】:

  • 还有{ RC = {1, 2, 3, 4}, ... }的可能解决方案
  • 这与您的第一个示例类似,但 aster 执行 map["key"] = { 1, 2, 3, 4 }print(table.maxn(map)); 返回 0 并且 for key, value in ipairs(maxn) do ... end 也不会进入循环。我不确定我做错了什么。顺便提一句。键可以是任何字符串,当我将它添加到“地图”时,数字列表(基本上是标识符列表)永远不会为空
  • @memoryofadream ipairs 仅按编号索引元素。从 1 到第一个非零元素。我会在 5 分钟后在答案中添加更多解释。
  • @memoryofadream 扩展了答案。查看 EDITED 部分,尤其是最后一个代码示例。希望现在更清楚了。
  • @Seagull 感谢您提供详细信息。我会在大约 4-5 小时后告诉你结果如何。
猜你喜欢
  • 2014-10-28
  • 1970-01-01
  • 2019-02-07
  • 2017-05-15
  • 2018-10-11
  • 2020-09-16
  • 2021-06-03
  • 2013-01-17
  • 1970-01-01
相关资源
最近更新 更多