web-dev-qa-db-fra.com

Lua - fusionner les tables?

Je dois fusionner deux tables, avec le contenu du deuxième contenu écrasant dans le premier si un élément donné est dans les deux J'ai regardé mais les bibliothèques standard ne semblent pas offrir cela. Où puis-je obtenir une telle fonction?

54
RCIX
for k,v in pairs(second_table) do first_table[k] = v end
83
Doug Currie

Voici ce que je propose à partir de la réponse de Doug Currie:

function tableMerge(t1, t2)
    for k,v in pairs(t2) do
        if type(v) == "table" then
            if type(t1[k] or false) == "table" then
                tableMerge(t1[k] or {}, t2[k] or {})
            else
                t1[k] = v
            end
        else
            t1[k] = v
        end
    end
    return t1
end
17
RCIX

Cela ne fonctionnerait-il pas correctement?


function merge(t1, t2)
    for k, v in pairs(t2) do
        if (type(v) == "table") and (type(t1[k] or false) == "table") then
            merge(t1[k], t2[k])
        else
            t1[k] = v
        end
    end
    return t1
end
10
James

Pour la fusion de table d'index numérique:

for k,v in pairs(secondTable) do table.insert(firstTable, v) end
3
Jimmy liu

Voici la version itérative pour la fusion en profondeur car je n'aime pas les débordements de pile potentiels de récursif.

local merge_task = {}
function merge_to_left_o(orig, new)
   merge_task[orig] = new

   local left = orig
   while left ~= nil do
      local right = merge_task[left]
      for new_key, new_val in pairs(right) do
         local old_val = left[new_key]
         if old_val == nil then
            left[new_key] = new_val
         else
            local old_type = type(old_val)
            local new_type = type(new_val)
            if (old_type == "table" and new_type == "table") then
               merge_task[old_val] = new_val
            else
               left[new_key] = new_val
            end
         end
      end
      merge_task[left] = nil
      left = next(merge_task)
   end
end
2
Oleg V. Volkov

La réponse de Doug Currie est la plus simple dans la plupart des cas. Si vous avez besoin d'une fusion plus robuste des tables, utilisez la méthode merge() de la bibliothèque Penlight .

require 'pl'
pretty.dump(tablex.merge({a=1,b=2}, {c=3,d=4}, true))

-- {
--   a = 1,
--   d = 4,
--   c = 3,
--   b = 2
-- }
2
Blackcoat

Je préférais la version James pour sa simplicité et l’utilisais dans utils.lua; j’ai ajouté une vérification du type de table pour la gestion des erreurs.

function merge(a, b)
    if type(a) == 'table' and type(b) == 'table' then
        for k,v in pairs(b) do if type(v)=='table' and type(a[k] or false)=='table' then merge(a[k],v) else a[k]=v end end
    end
    return a
end

Merci pour cette fonction intéressante qui devrait faire partie de la classe table afin que vous puissiez appeler a:merge(b) mais que table.merge = function(a, b) ... ne fonctionne pas pour moi. Pourrait même être compressé à une ligne pour les vrais nerds :)

0
hexerei software
for k,v in pairs(t2) do t1[k] = v end

clé pour la solution de chaîne

0
TimChang