159 lines
2.3 KiB
Lua
159 lines
2.3 KiB
Lua
local functional = {}
|
|
|
|
local t_iterate = futil.table.iterate
|
|
local t_insert = table.insert
|
|
|
|
function functional.noop()
|
|
-- the NOTHING function does nothing.
|
|
end
|
|
|
|
function functional.identity(x)
|
|
return x
|
|
end
|
|
|
|
function functional.izip(...)
|
|
local is = { ... }
|
|
if #is == 0 then
|
|
return functional.noop
|
|
end
|
|
|
|
return function()
|
|
local t = {}
|
|
for i in t_iterate(is) do
|
|
local v = i()
|
|
if v ~= nil then
|
|
t_insert(t, v)
|
|
else
|
|
return
|
|
end
|
|
end
|
|
|
|
return t
|
|
end
|
|
end
|
|
|
|
function functional.zip(...)
|
|
local is = {}
|
|
for t in t_iterate({ ... }) do
|
|
t_insert(is, t_iterate(t))
|
|
end
|
|
return functional.izip(unpack(is))
|
|
end
|
|
|
|
function functional.imap(func, ...)
|
|
local zipper = functional.izip(...)
|
|
return function()
|
|
local args = zipper()
|
|
if args then
|
|
return func(unpack(args))
|
|
end
|
|
end
|
|
end
|
|
|
|
function functional.map(func, ...)
|
|
local zipper = functional.zip(...)
|
|
return function()
|
|
local args = zipper()
|
|
if args then
|
|
return func(unpack(args))
|
|
end
|
|
end
|
|
end
|
|
|
|
function functional.apply(func, t)
|
|
local t2 = {}
|
|
for k, v in pairs(t) do
|
|
t2[k] = func(v)
|
|
end
|
|
return t2
|
|
end
|
|
|
|
function functional.reduce(func, t, initial)
|
|
local i = t_iterate(t)
|
|
if not initial then
|
|
initial = i()
|
|
end
|
|
local next = i()
|
|
while next do
|
|
initial = func(initial, next)
|
|
next = i()
|
|
end
|
|
return initial
|
|
end
|
|
|
|
function functional.partial(func, ...)
|
|
local args = { ... }
|
|
return function(...)
|
|
return func(unpack(args), ...)
|
|
end
|
|
end
|
|
|
|
function functional.compose(a, b)
|
|
return function(...)
|
|
return a(b(...))
|
|
end
|
|
end
|
|
|
|
function functional.ifilter(pred, i)
|
|
local v
|
|
return function()
|
|
v = i()
|
|
while v ~= nil and not pred(v) do
|
|
v = i()
|
|
end
|
|
return v
|
|
end
|
|
end
|
|
|
|
function functional.filter(pred, t)
|
|
return functional.ifilter(pred, t_iterate(t))
|
|
end
|
|
|
|
function functional.iall(i)
|
|
while true do
|
|
local v = i()
|
|
if v == false then
|
|
return false
|
|
elseif v == nil then
|
|
return true
|
|
end
|
|
end
|
|
end
|
|
|
|
function functional.all(t)
|
|
for i = 1, #t do
|
|
if not t[i] then
|
|
return false
|
|
end
|
|
end
|
|
|
|
return true
|
|
end
|
|
|
|
function functional.iany(i)
|
|
while true do
|
|
local v = i()
|
|
if v == nil then
|
|
return false
|
|
elseif v then
|
|
return true
|
|
end
|
|
end
|
|
end
|
|
|
|
function functional.any(t)
|
|
for i = 1, #t do
|
|
if t[i] then
|
|
return true
|
|
end
|
|
end
|
|
return false
|
|
end
|
|
|
|
function functional.wrap(f)
|
|
return function(...)
|
|
return f(...)
|
|
end
|
|
end
|
|
|
|
futil.functional = functional
|