Lua table 带字符串键的数字索引不起作用?

Lua table with string keys does not work with number indexing?

我是 Lua 的初学者。

我认为使用字符串键将值推送到 table 也会自动进行数字索引,但我认为我错了。

我的代码:

local t = {}
t.name = "John"
t.age = 30
print("Name : " .. t.name .. "\nAge : " .. t.age)

虽然这段代码工作正常并打印出预期的结果,

Name : John
Age : 30

如果我尝试以这种方式打印结果,

print("Name : " .. t[1] .. "\nAge : " .. t[2])

我收到以下错误:

lua: main.lua:5: attempt to concatenate a nil value (field '?')
stack traceback:
    main.lua:5: in main chunk
    [C]: in ?

这是否意味着我无法在不知道键字符串的情况下使用带有数字索引的 for 遍历 table?

如果是这样,是否有任何解决方法可以使这两种方式都起作用?

将值添加到 table 不会像使用索引键那样添加它们。当您使用 table 中的值时,您可以使用点符号访问它们,如第一个示例中所示,或者像这样:

print("Name : " .. t["name"] .. "\nAge : " .. t["age"])

您可以使用函数 pairs 遍历 table 中的键值对,如下所示:

for k, v in pairs(t) do
    print(k, v)
end

如果你想使用索引而不是字符串键,你可以这样设置:

local t = {
    "John",
    30,
}
print("Name : " .. t[1].. "\nAge : " .. t[2])

当您这样做时,table t 中的值会自动为每个值分配整数索引。如果要逐一迭代,可以用ipairs迭代:

for i, v in ipairs(t) do
    print(i, v)
end

您可以使用 metatable 为自己破解数字索引,但这将完全无用,因为在具有非数字、非连续索引的 table 中,顺序未指定。

local mt = { __index = function(t, n)
                 assert(n > 0)
                 for k, v in pairs(t) do
                     n = n - 1
                     if n == 0 then
                         return v
                     end
                 end
           end }

local t = {}
setmetatable(t, mt)
t.name = "John"
t.age = 30
print("Name : " .. t.name .. "\nAge : " .. t.age)
print("Name : " .. t[1] .. "\nAge : " .. t[2])

连续多次执行上述脚本会发现问题所在:

$ lua test.lua 
Name : John
Age : 30
Name : John
Age : 30
$ lua test.lua 
Name : John
Age : 30
Name : 30
Age : John