lua-users home
lua-l archive

[Date Prev][Date Next][Thread Prev][Thread Next] [Date Index] [Thread Index]


On 23/01/2010 07:53, Florian Weimer wrote:
* Joe Andresen:

I went to the lua users org site to get the code but i seem to get the error

..\Content\Scripts\LuaPickle.lua:13: attempt to call a table value

which is the line

clone = function (t) local nt={}; for i, v in t do nt[i]=v end return nt end
I think this has to be written "for i, v in pairs(t)" in Lua 5.1.


I've made changes so it works with 5.1. I don't remember exactly what I've changed, but my changes are public domain.

Cheers,

Andre
----------------------------------------------
-- Pickle.lua
-- A table serialization utility for lua
-- Steve Dekorte, http://www.dekorte.com, Apr 2000
-- Freeware
----------------------------------------------

local Pickle = {
	clone = function (t) local nt={}; system_lib.for_each(t, function(i, v) nt[i] = v end) return nt end
}

function Pickle:pickle_(root)
	if system_lib.type_of(root) ~= system_lib.TABLE then 
		system_lib.error('can only pickle tables')
	end
	self._tableToRef = {}
	self._refToTable = {}
	local savecount = 0
	self:ref_(root)
	local s = ''

	while system_lib.get_n(self._refToTable) > savecount do
		savecount = savecount + 1
		local t = self._refToTable[savecount]
		s = s .. '{\n'
		system_lib.for_each(t, function(i, v)
			s = s .. '[' .. self:value_(i) .. ']=' .. self:value_(v) .. ',\n'
		end)
		s = s .. '},\n'
	end

	return '{' .. s .. '}'
end

function Pickle:value_(v)
	local	vtype = system_lib.type_of(v)
	if	vtype == system_lib.STRING then return system_lib.quote(v)
	elseif	vtype == system_lib.NUMBER then return v
	elseif vtype == system_lib.BOOLEAN then return v and 'true' or 'false'
	elseif	vtype == system_lib.TABLE then return '{' .. self:ref_(v) .. '}'
	else	--error('pickle a '..type(v)..' is not supported')
	end  
end

function Pickle:ref_(t)
	local ref = self._tableToRef[t]
	if not ref then 
		if t == self then system_lib.error('can\'t pickle the pickle class') end
		system_lib.insert(self._refToTable, t)
		ref = system_lib.get_n(self._refToTable)
		self._tableToRef[t] = ref
	end
	return ref
end

----------------------------------------------
-- pickle
----------------------------------------------

system_lib.pickle = function(t)
	return Pickle:clone():pickle_(t)
end

----------------------------------------------
-- unpickle
----------------------------------------------

system_lib.unpickle = function(s)
	if system_lib.type_of(s) ~= system_lib.STRING then
		system_lib.error('can only unpickle strings')
	end
	local tables = system_lib.eval('return ' .. s)
  
	for tnum = 1, system_lib.get_n(tables) do
		local t = tables[tnum]
		local tcopy = {}; system_lib.for_each(t, function(i, v) tcopy[i] = v end)
		system_lib.for_each(tcopy, function(i, v)
			local ni, nv
			if system_lib.type_of(i) == system_lib.TABLE then ni = tables[i[1]] else ni = i end
			if system_lib.type_of(v) == system_lib.TABLE then nv = tables[v[1]] else nv = v end
			t[ni] = nv
		end)
	end
	return tables[1]
end