Page 1 of 2

Lua-enumerable is a library of table manipulation functions

Posted: Wed Jun 22, 2011 6:50 am
by mikelovesrobots
https://github.com/mikelovesrobots/lua-enumerable

Code: Select all

lua-enumerable is a quick and dirty port of the ruby Enumerable library plus some extras.

It's a native lua library.  Installation is as simple as dropping it in your project and requiring it:

    require("lua-enumerable")
    
Synopsis:

    local test = {1,2,3}

    table.each(test, function (x) print(x) end)
    -- 1
    -- 2
    -- 3

    table.times(4, function (x) print(x) end)
    -- 1
    -- 2
    -- 3
    -- 4

    table.collect(test, function (x) return x + 1 end)
    -- {2, 3, 4}

    table.select(test, function (x) return x < 3 end)
    -- {1, 2}
    
    table.reject(test, function (x) return x < 3 end)
    -- {3}

    table.partition(test, function (x) return x < 3 end)
    -- {1, 2}, {3}

    table.includes(test, 3)
    -- true

    table.detect(test, function (x) return x == 3 end)
    -- 3

    table.detect(test, function (x) return x == 4 end)
    -- nil

    table.merge({4}, test)
    -- {4,1,2,3}

Provides some array manipulation functions:

    table.pop(test)
    -- returns 3, test is mutated to {1,2}
     
    table.shift(test)
    -- returns 1, test is mutated to {2,3}

    table.unshift(test, 4)
    -- {4, 1, 2, 3}

    table.push(test, 4)
    -- {1, 2, 3, 4}

Grab a random element with:

    table.random(test)
    -- {3}
    
    table.random(test)
    -- {2}

Oh, look, boolean tests too for sexy if statements:

    table.empty({})
    -- true
    
    table.empty(nil)
    -- true

    table.empty({1,2,3})
    -- false

    table.present({})
    -- false
    
    table.present(nil)
    -- false

    table.present({1,2,3})
    -- true

And some useful bits:

    table.reverse({1,2,3})
    -- {3,2,1}

    table.dup({1,2,3})
    -- {1,2,3}

Re: Lua-enumerable a port of useful table manipulation funct

Posted: Wed Jun 22, 2011 7:12 am
by kikito
Hi there!

I like this. (I'm missing some automated tests though).

Re: Lua-enumerable a port of useful table manipulation funct

Posted: Wed Jun 22, 2011 7:55 am
by mikelovesrobots
kikito wrote:Hi there!

I like this. (I'm missing some automated tests though).
Yeah. It was missing tests. There is now.

Re: Lua-enumerable is a library of table manipulation functi

Posted: Wed Jun 22, 2011 8:43 am
by BlackBulletIV
I like the looks of this, some great functions there. One thing though; this code

Code: Select all

table.pop = function(list)
  return table.remove(list)
end

table.push = function(list, item)
  return table.insert(list, item)
end
would be more efficiently re-factored as

Code: Select all

table.pop = table.remove
table.push = table.insert

Re: Lua-enumerable is a library of table manipulation functi

Posted: Wed Jun 22, 2011 9:25 am
by bartbes
Except it's not the same. (You can't pass an index to pop now, but you could with your code.)

Re: Lua-enumerable is a library of table manipulation functi

Posted: Wed Jun 22, 2011 11:28 am
by BlackBulletIV
bartbes wrote:Except it's not the same. (You can't pass an index to pop now, but you could with your code.)
Yeah I know, but it's pretty simple for the user not to do that.

Anyway, it probably won't save much at all, though function calls do add up when called in the hundreds of thousands.

Re: Lua-enumerable is a library of table manipulation functi

Posted: Wed Jun 22, 2011 12:46 pm
by Robin
Fun fact: there is a table.foreach function and a table.foreachi function (the latter of which is equivalent to your table.each function), but they are deprecated now.

Re: Lua-enumerable is a library of table manipulation functi

Posted: Wed Jun 22, 2011 4:11 pm
by RPG

Code: Select all

function table.shuffle(array)
  local b
  for k, v in pairs(array) do
    b = math.random(1,#array)
    array[k] = array[b]
    array[b] = v
  end
end

Re: Lua-enumerable is a library of table manipulation functi

Posted: Wed Jun 22, 2011 4:25 pm
by Robin
RPG wrote:

Code: Select all

function table.shuffle(array)
  local b
  for k, v in pairs(array) do
    b = math.random(1,#array)
    array[k] = array[b]
    array[b] = v
  end
end
I believe this implementation is incorrect (it most certainly is if the table contains non-array entries).

I think a correct one is:

Code: Select all

function table.shuffle(array)
    for i = #array, 2 do
        local j = math.random(1, i)
        array[i], array[j] = array[j], array[i]
    end
end
From Wikipedia, this algorithm is known as Fisher-Yates shuffle.

Re: Lua-enumerable is a library of table manipulation functi

Posted: Wed Jun 22, 2011 5:33 pm
by vrld
Neat. I use these functions regularly, although under different names (each/collect -> map, select/reject -> filter) and not so much in game programming.

This one is also very useful:

Code: Select all

function table.fold(t, init, f)
    for k,v in pairs(t) do
        init = f(init, v, k)
    end
    return init
end

sum = table.fold({1,2,3,4,5}, 0, function(a,b) return a+b end) --> 15
prod = table.fold({1,2,3,4,5}, 1, function(a,b) return a*b end) --> 120
-- just cause:
function table.map(t, f)
    return table.fold(t, {}, function(a, v,k) a[k] = f(v,k); return a end)
end
table.map({1,2,3,4,5}, function(a) return a * a end) --> {1, 4, 9, 16, 25}