Text Processing

lua-users home
wiki

Especially for Perl programmers, Lua's lack of text processing power can be an annoyance. Here are some mostly Perl-inspired routines to take away some of the pain:

[!] VersionNotice: The below code pertains to an older Lua version, Lua 4. It does not run as is under Lua 5.

-- Write a line adding \n to the end

--   [fp]: file handle

--   s: string to write

function writeLine(fp, s)

  if not s then s, fp = fp, nil end

  if fp then write(fp, s .. "\n")

  else write(s .. "\n")

  end

end



-- Remove any final \n from a string.

--   s: string to process

-- returns

--   s: processed string

function chomp(s)

  return gsub(s, "\n$", "")

end



-- Escape a string to be used as a pattern

--   s: string to process

-- returns

--   s: processed string

function escapePattern(s)

  s = gsub(s, "(%W)", "%%%1")

  return s

end



-- Escape a string to be used as a shell token (quote spaces and \s)

--   s: string to process

-- returns

--   s: processed string

function escapeShell(s)

  s = gsub(s, "([ %(%)])", "\\%1")

  return s

end



-- Turn a list of strings into a sep-separated string

--   sep: separator

--   l: list of strings to join

-- returns

--   s: joined up string

function join(sep, l)

  local len = getn(l)

  if len == 0 then return "" end

  local s = l[1]

  for i = 2, len do s = s .. sep .. l[i] end

  return s

end



-- Justify a string

--   s: string to justify

--   width: width to justify to (+ve means right-justify; negative

--     means left-justify)

--   [padder]: string to pad with (" " if omitted)

-- returns

--   s: justified string

function pad(s, width, padder)

  padder = strrep(padder or " ", abs(width))

  if width < 0 then return strsub(padder .. s, width) end

  return strsub(s .. padder, 1, width)

end



-- Wrap a string into a paragraph

--   s: string to wrap

--   w: width to wrap to [78]

--   i1: indent of first line [0]

--   i2: indent of subsequent lines [0]

-- returns

--   s: wrapped paragraph

function wrap(s, w, i1, i2)

  w = w or 78

  i1 = i1 or 0

  i2 = i2 or 0

  affirm(i1 < w and i2 < w,

         "wrap: the indents must be less than the line width")

  s = strrep(" ", i1) .. s

  local lstart, len = 1, strlen(s)

  while len - lstart > w do

    local i = lstart + w

    while i > lstart and strsub(s, i, i) ~= " " do i = i - 1 end

    local j = i

    while j > lstart and strsub(s, j, j) == " " do j = j - 1 end

    s = strsub(s, 1, j) .. "\n" .. strrep(" ", i2) ..

      strsub(s, i + 1, -1)

    local change = i2 + 1 - (i - j)

    lstart = j + change

    len = len + change

  end

  return s

end



-- readLines: read _INPUT into a list of lines

-- returns

--   line: list of lines

function readLines()

  local line = {}

  repeat

    local l = read("*l")

    if not l then break end

    tinsert(line, l)

  until nil

  return line

end


RecentChanges · preferences
edit · history
Last edited October 30, 2010 6:18 pm GMT (diff)