elua: use string buffer in all places for format plus extra optimizations

This commit is contained in:
Daniel Kolesa 2014-05-09 11:50:37 +01:00 committed by Daniel Kolesa
parent a6e50fa9c7
commit 3da9de3d41
1 changed files with 18 additions and 17 deletions

View File

@ -179,8 +179,6 @@ ffi.cdef [[
int isdigit(int c); int isdigit(int c);
]] ]]
local char = string.char
local tconc = table.concat
local fmt = string.format local fmt = string.format
local pcall = pcall local pcall = pcall
local error = error local error = error
@ -226,6 +224,7 @@ local Str_Buf = ffi.metatype("Str_Buf", {
self.len = len + 1 self.len = len + 1
end, end,
append_str = function(self, str, strlen) append_str = function(self, str, strlen)
if type(str) == "string" then strlen = strlen or #str end
local strp = cast("const char*", str) local strp = cast("const char*", str)
strlen = strlen or C.strlen(strp) strlen = strlen or C.strlen(strp)
local len = self.len local len = self.len
@ -240,13 +239,15 @@ local Str_Buf = ffi.metatype("Str_Buf", {
getmetatable("").__mod = function(fmts, params) getmetatable("").__mod = function(fmts, params)
if not fmts then return nil end if not fmts then return nil end
if type(params) ~= "table" then params = { params } end if type(params) ~= "table" then
params = { params }
end
local buf, nbuf = Str_Buf(), Str_Buf()
local s = cast("const char*", fmts) local s = cast("const char*", fmts)
local buf = {} local c, s = s[0], s + 1
local c
c, s = s[0], s + 1
local argn = 1 local argn = 1
local nbuf = Str_Buf()
while c ~= 0 do while c ~= 0 do
if c == 37 then -- % if c == 37 then -- %
c, s = s[0], s + 1 c, s = s[0], s + 1
@ -263,9 +264,9 @@ getmetatable("").__mod = function(fmts, params)
c, s = s[0], s + 1 c, s = s[0], s + 1
end end
if bytes[c] then if bytes[c] then
buf[#buf + 1] = n buf:append_str(n)
buf[#buf + 1] = "$" buf:append_char(36) -- $
buf[#buf + 1] = char(c) buf:append_char(c)
else else
nbuf:append_char(c) nbuf:append_char(c)
local idx = tonumber(n) or n local idx = tonumber(n) or n
@ -273,7 +274,7 @@ getmetatable("").__mod = function(fmts, params)
params[idx]) params[idx])
nbuf:clear() nbuf:clear()
if stat then if stat then
buf[#buf + 1] = val buf:append_str(val)
else else
local argerr = (type(idx) == "number") local argerr = (type(idx) == "number")
and ("#" .. idx) and ("#" .. idx)
@ -292,20 +293,20 @@ getmetatable("").__mod = function(fmts, params)
params[argn]) params[argn])
nbuf:clear() nbuf:clear()
if stat then if stat then
buf[#buf + 1] = val buf:append_str(val)
else else
error("bad argument #" .. argn .. " to '%' " error("bad argument #" .. argn .. " to '%' "
.. val:match("%(.+%)"), 2) .. val:match("%(.+%)"), 2)
end end
if c then buf[#buf + 1] = char(c) end if c then buf:append_char(c) end
argn = argn + 1 argn = argn + 1
end end
else else
buf[#buf + 1] = char(c) buf:append_char(c)
end end
c, s = s[0], s + 1 c, s = s[0], s + 1
end end
return tconc(buf) return tostr(buf)
end end
return M return M