Common Functions

lua-users home
wiki

Some commonly used functions (stolen from messageboards, other wiki pages, PiL) are listed below- feel free to improve them.

String Library

-- all/string.lua (all.string)

-- A Lua Library (ALL) - string utility functions.

-- This is compatible with Lua 5.1.

-- Licensed under the same terms as Lua itself.--DavidManura

module("all.string", package.seeall)



function import()

  local env = getfenv(2)

  for k,v in pairs(all.string) do env[k] = v end

end



-- remove trailing and leading whitespace from string.

-- http://en.wikipedia.org/wiki/Trim_(8programming)

function trim(s)

  -- from PiL2 20.4

  return (s:gsub("^%s*(.-)%s*$", "%1"))

end



-- remove leading whitespace from string.

-- http://en.wikipedia.org/wiki/Trim_(8programming)

function ltrim(s)

  return (s:gsub("^%s*", ""))

end



-- remove trailing whitespace from string.

-- http://en.wikipedia.org/wiki/Trim_(8programming)

function rtrim(s)

  local n = #s

  while n > 0 and s:find("^%s", n) do n = n - 1 end

  return s:sub(1, n)

end

-- The following more obvious implementation is generally not

-- as efficient, particularly for long strings since Lua pattern matching

-- starts at the left (though in special cases it is more efficient).

-- Related discussion on p.197 of book "Beginning Lua Programming".

--[[

function rtrim(s) return (s:gsub("%s*$", "")) end

]]



-- substitute variables into string.

-- Example: subst("a=$(a),b=$(b)", {a=1, b=2}) --> "a=1,b=2".

function subst(s, t)

  -- note: handle {a=false} substitution

  s = s:gsub("%$%(([%w_]+)%)", function(name)

    local val = t[name]

    return val ~= nil and tostring(val)

  end)

  return s

end



-- Other ideas...

-- This library needs one good split function.



-- [mjc 6/12/2008] here is my basic split implementation.

-- takes a string and a pattern to split with. returns a table 

-- of words that have been seperated at the pattern (does not 

-- include the pattern in any words in the returned table).

function split(str, patt)

	vals = {}; valindex = 0; word = ""

	-- need to add a trailing separator to catch the last value.

	str = str .. patt

	for i = 1, string.len(str) do

	

		cha = string.sub(str, i, i)

		if cha ~= patt then

			word = word .. cha

		else

			if word ~= nil then

				vals[valindex] = word

				valindex = valindex + 1

				word = ""

			else

				-- in case we get a line with no data.

				break

			end

		end 

		

	end	

	return vals

end



Tests.

-- alltest.lua

-- Test suite for all library.



require "all.string" :import()



function assert_equal(a, b)

  if a ~= b then error(tostring(a) .. " == " .. tostring(b), 2) end

end



assert_equal(trim(""), "")

assert_equal(trim("   "), "")

assert_equal(trim("12"), "12")

assert_equal(trim(" 12 "), "12")

assert_equal(trim("  1 2  "), "1 2")

assert_equal(trim("\r\n\t\f 1\r\n\t\f\ "), "1")



assert_equal(ltrim(""), "")

assert_equal(trim("   "), "")

assert_equal(ltrim("12"), "12")

assert_equal(ltrim(" 12 "), "12 ")

assert_equal(ltrim("  1 2  "), "1 2  ")

assert_equal(ltrim("\r\n\t\f 1\r\n\t\f\ "), "1\r\n\t\f ")



assert_equal(rtrim(""), "")

assert_equal(trim("   "), "")

assert_equal(rtrim("12"), "12")

assert_equal(rtrim(" 12 "), " 12")

assert_equal(rtrim("  1 2  "), "  1 2")

assert_equal(rtrim("\r\n\t\f 1\r\n\t\f\ "), "\r\n\t\f\ 1")



assert_equal(subst("", {}), "")

assert_equal(subst("aa=$(aa),bb_=$(bb_)", {aa=1,bb_=2}), "aa=1,bb_=2")

assert_equal(subst("a=$(a)", {a=false}), "a=false")

assert_equal(subst("a=$(a),b=$(b),c=$(c)", {a=4,b=2,c=nil}), "a=4,b=2,c=$(c)")



print("done")

Patterns Library

-- all/pattern.lua (all.pattern)

-- A Lua Library (ALL) - pattern utility functions.

-- This is compatible with Lua 5.1.

-- Licensed under the same terms as Lua itself.--DavidManura

module("all.pattern", package.seeall)



function import()

  local env = getfenv(2)

  for k,v in pairs(all.pattern) do env[k] = v end

end



-- Remove whitespace from pattern.

-- Patterns may be expressed more readably with

-- extra whitespace and then filtered through this function

-- to remove this whitespace for processing.

-- This function is inspired by the //x regex option in Perl.

-- If the final pattern requires whitespace, escape it (e.g. "% ").

-- Example: ("(x y)"):gsub(px" ^ %( . % . %) $ ", "t") --> "t"

function px(s)

  local n = 1

  while true do

    while true do -- removes spaces

      local _, ne, np = s:find("^[^%s%%]*()%s*", n)

      n = np

      if np - 1 ~= ne then s = s:sub(1, np - 1) .. s:sub(ne + 1)

      else break end

    end

    local m = s:match("%%(.?)", n) -- skip magic chars

    if m == "b" then n = n + 4

    elseif m then n = n + 2

    else break end

  end

  return s

end



-- Lua pattern for matching Lua identifier.

-- Warning: wrongly matches Lua keywords too.

pat_id = "([%a_][%w_]*)"



-- Lua pattern for matching Lua single line comment.

pat_scomment = "(%-%-[^\n]*)"



-- Lua pattern for matching Lua multi-line comment.

pat_mcomment = "(%-%-%[(=*)%[.-%]%2%])"



-- Other ideas....



-- Possibly add more Lua parsing like in Perl Text-Balanced.

-- Note: not all fragments can be parsed with plain Lua patterns,

-- though regexes maybe.  There could possibly be a series of

-- find_* functions.  For example, find_luastring(s, n) to find

-- Lua syntax string at index n in string s.



-- Possibly add a pure Lua implementation for matching patterns

-- with alternations as in the regex "(yes|no)+" construct.

-- Or maybe add a gmatch that takes multiple patterns and matches

-- any of the patterns.

Tests.

require "all.pattern" :import()



function assert_equal(a, b)

  if a ~= b then error("<" .. tostring(a) .. "==" .. tostring(b) .. ">", 2) end

end



assert_equal(px"", "")

assert_equal(px"   \f\n\r\t\f", "")

assert_equal(px" ^ %(  .-  %) $ ", "^%(.-%)$")

assert_equal(px" 1%%% 2%% %%% %.%b %%%  %a  %b%% % . . %a",

               "1%%% 2%%%%% %.%b %%%%a%b%%% ..%a")

assert_equal(px"%", "%") -- actually invalid pattern

assert_equal(("(x y)"):gsub(px" ^ %( . % . %) $ ", "t"), "t")



assert_equal(("_"):match("^" .. pat_id), "_")

assert_equal(("A1_"):match("^" .. pat_id), "A1_")



assert_equal(("--\n2"):match("^" .. pat_scomment), "--")

assert_equal(("--123\n2"):match("^" .. pat_scomment), "--123")



assert_equal(("--[[ ] ]] "):match("^" .. pat_mcomment), "--[[ ] ]]")

assert_equal(("--[[ ]] ]]"):match("^" .. pat_mcomment), "--[[ ]]")

assert_equal(("--[==[ ]] ]==] ]==]"):match("^" .. pat_mcomment),

              "--[==[ ]] ]==]")

See Also


RecentChanges · preferences
edit · history
Last edited December 25, 2009 4:45 am GMT (diff)