local seq = { 1, 2, 3, 4, 5 } -- obviously, it's a sequence.
local non_seq = { 1, 2, 3, nil, 5 } -- but it's not.
Run Code Online (Sandbox Code Playgroud)
序列的定义:长度运算符
这个问题在《Programming in Lua 4st》第五章中。
如有任何意见,我将不胜感激
您链接了答案所需的信息。
Lua 5.3 中的边界定义为:
(border == 0 or t[border] ~= nil) and t[border + 1] == nil
Run Code Online (Sandbox Code Playgroud)
正确的序列只能包含一个边界。然而,为了涵盖其他一些条件,代码确实需要更多的跑腿工作,例如验证索引可以在序列中。
function is_sequence(t)
local borders = 0
if t[1] ~= nil then -- all sequences must start at 1.
for index in pairs(t) do
if natural_index(index) and t[index + 1] == nil then
borders = borders + 1
if borders > 1 then
break
end
end
end
end
return borders == 1 or valid_no_borders(t) and borders == 0
end
function natural_index(index)
return type(index) == "number" and index > 0 and math.floor(index) == index
end
function valid_no_borders(t)
result = true
for k in pairs(t) do
if natural_index(k) then
result = false
break
end
end
return t[1] == nil and result
end
Run Code Online (Sandbox Code Playgroud)
function is_sequence(t)
local borders = 0
if t[1] ~= nil then -- all sequences must start at 1.
for index in pairs(t) do
if natural_index(index) and t[index + 1] == nil then
borders = borders + 1
if borders > 1 then
break
end
end
end
end
return borders == 1 or valid_no_borders(t) and borders == 0
end
function natural_index(index)
return type(index) == "number" and index > 0 and math.floor(index) == index
end
function valid_no_borders(t)
result = true
for k in pairs(t) do
if natural_index(k) then
result = false
break
end
end
return t[1] == nil and result
end
Run Code Online (Sandbox Code Playgroud)
结果
-- Tests
local seqs = {
{ 1, 2, 3, 4, 5 }, -- obviously, it's a sequence.
{ 1, 2, 3, 4, ["potato"] = 5 },
{ 1, 2, [3.3] = 3 },
{ [2.2] = 2 },
{ [-1] = -1, [0] = 0, 1, 2, 3 },
{},
}
for _, v in ipairs(seqs) do
print("seq: ", is_sequence(v))
end
local non_seqs ={
{ 1, 2, 3, nil, 5 }, -- but it's not.
{ [2] = 2 },
}
for _, v in ipairs(non_seqs) do
print("non_seq: ", is_sequence(v))
end
Run Code Online (Sandbox Code Playgroud)
此方法的优点是仅对每个元素求值一次,如果表不是有效序列,则尽早退出。