在lua中创建单个迭代解包函数的更好方法



Lua 解包功能仅适用于简单表,所以我编写了一个可以解压缩复杂表的函数。它工作正常,但我正在寻找更好的方法来编写这样的函数。代码如下:

c = {1,2,{3,4},{{5,6},{7,8}}}
vt = {}
function convertToSimpleTable(t,vacantTable)
    if type(t)=="table" then
        for _,val in ipairs(t) do
            if type(val)=="table" then
                convertToSimpleTable(val,vacantTable)
            else
                table.insert(vacantTable,val)
            end
        end
        return vacantTable
    else
        return {t}
    end
end
print(unpack(convertToSimpleTable(c,vt)))

输出:

1   2   3   4   5   6   7   8

为了使这个函数工作,我需要提供一个空表,因为如果我在函数内初始化一个表,它会重新初始化,因为该函数是迭代的,因此给出了错误的结果

只需添加:

vacantTable=vacantTable or {}

到函数的开头。或者创建第二个函数并从基本包装器调用这个函数:

function convertToSimpleTable(t)
  return convertToSimpleTable_impl(t, {})
end 

另一种可能性:

c = {1,2,{3,4},{{5,6},{7,8}}}
function convertToSimpleTable(t)
  local ans = {}
  for _,t in ipairs(t) do
    if type(t) == 'table' then
      for _,t in ipairs(convertToSimpleTable(t)) do
        ans[#ans+1] = t
      end
    else
      ans[#ans+1] = t
    end
  end
  return ans
end
print(unpack(convertToSimpleTable(c)))

特别感谢 Dan200 编写了这段出色的代码。

local function serializeImpl( t, tTracking, sIndent )
    local sType = type(t)
    if sType == "table" then
        if tTracking[t] ~= nil then
            error( "Cannot serialize table with recursive entries", 0 )
        end
        tTracking[t] = true
        if next(t) == nil then
            -- Empty tables are simple
            return "{}"
        else
            -- Other tables take more work
            local sResult = "{n"
            local sSubIndent = sIndent .. "  "
            local tSeen = {}
            for k,v in ipairs(t) do
                tSeen[k] = true
                sResult = sResult .. sSubIndent .. serializeImpl( v, tTracking, sSubIndent ) .. ",n"
            end
            for k,v in pairs(t) do
                if not tSeen[k] then
                    local sEntry
                    if type(k) == "string" and not g_tLuaKeywords[k] and string.match( k, "^[%a_][%a%d_]*$" ) then
                        sEntry = k .. " = " .. serializeImpl( v, tTracking, sSubIndent ) .. ",n"
                    else
                        sEntry = "[ " .. serializeImpl( k, tTracking, sSubIndent ) .. " ] = " .. serializeImpl( v, tTracking, sSubIndent ) .. ",n"
                    end
                    sResult = sResult .. sSubIndent .. sEntry
                end
            end
            sResult = sResult .. sIndent .. "}"
            return sResult
        end
    elseif sType == "string" then
        return string.format( "%q", t )
    elseif sType == "number" or sType == "boolean" or sType == "nil" then
        return tostring(t)
    else
        error( "Cannot serialize type "..sType, 0 )
    end
end
function serialize( t )
    local tTracking = {}
    return serializeImpl( t, tTracking, "" )
end

PS:最初是为一个名为Computer Craft的Minecraft模组制作的,因此某些功能可能无法正常工作。

最新更新