162 lines
2.5 KiB
Lua
162 lines
2.5 KiB
Lua
futil.math = {}
|
|
|
|
local floor = math.floor
|
|
local huge = math.huge
|
|
local max = math.max
|
|
local min = math.min
|
|
|
|
function futil.math.idiv(a, b)
|
|
local rem = a % b
|
|
return (a - rem) / b, rem
|
|
end
|
|
|
|
function futil.math.bound(m, v, M)
|
|
return max(m, min(v, M))
|
|
end
|
|
|
|
function futil.math.in_bounds(m, v, M)
|
|
return m <= v and v <= M
|
|
end
|
|
|
|
local in_bounds = futil.math.in_bounds
|
|
|
|
function futil.math.is_integer(v)
|
|
return floor(v) == v
|
|
end
|
|
|
|
local is_integer = futil.math.is_integer
|
|
|
|
function futil.math.is_u8(i)
|
|
return (type(i) == "number" and is_integer(i) and in_bounds(0, i, 0xFF))
|
|
end
|
|
|
|
function futil.math.is_u16(i)
|
|
return (type(i) == "number" and is_integer(i) and in_bounds(0, i, 0xFFFF))
|
|
end
|
|
|
|
function futil.math.sum(t, initial)
|
|
local sum
|
|
local start
|
|
if initial then
|
|
sum = initial
|
|
start = 1
|
|
else
|
|
sum = t[1]
|
|
start = 2
|
|
end
|
|
|
|
for i = start, #t do
|
|
sum = sum + t[i]
|
|
end
|
|
|
|
return sum
|
|
end
|
|
|
|
function futil.math.isum(i, initial)
|
|
local sum
|
|
|
|
if initial == nil then
|
|
sum = i()
|
|
else
|
|
sum = initial
|
|
end
|
|
|
|
local v = i()
|
|
|
|
while v do
|
|
sum = sum + v
|
|
v = i()
|
|
end
|
|
|
|
return sum
|
|
end
|
|
|
|
function futil.math.product(t, initial)
|
|
local product
|
|
local start
|
|
if initial then
|
|
product = initial
|
|
start = 1
|
|
else
|
|
product = t[1]
|
|
start = 2
|
|
end
|
|
|
|
for i = start, #t do
|
|
product = product * t[i]
|
|
end
|
|
|
|
return product
|
|
end
|
|
|
|
function futil.math.iproduct(i, initial)
|
|
local product
|
|
|
|
if initial == nil then
|
|
product = i()
|
|
else
|
|
product = initial
|
|
end
|
|
|
|
local v = i()
|
|
|
|
while v do
|
|
product = product * v
|
|
v = i()
|
|
end
|
|
|
|
return product
|
|
end
|
|
|
|
function futil.math.probabilistic_round(v)
|
|
return floor(v + math.random())
|
|
end
|
|
|
|
function futil.math.cmp(a, b)
|
|
return a < b
|
|
end
|
|
|
|
futil.math.deg2rad = math.deg
|
|
|
|
futil.math.rad2deg = math.rad
|
|
|
|
function futil.math.do_intervals_overlap(min1, max1, min2, max2)
|
|
return min1 <= max2 and min2 <= max1
|
|
end
|
|
|
|
-- i took one class from kahan and can't stop doing this
|
|
local function round(n)
|
|
local d = n % 1
|
|
local i = n - d
|
|
|
|
if i % 2 == 0 then
|
|
if d <= 0.5 then
|
|
return i
|
|
else
|
|
return i + 1
|
|
end
|
|
else
|
|
if d < 0.5 then
|
|
return i
|
|
else
|
|
return i + 1
|
|
end
|
|
end
|
|
end
|
|
|
|
function futil.math.round(number, mult)
|
|
if mult then
|
|
return round(number / mult) * mult
|
|
else
|
|
return round(number)
|
|
end
|
|
end
|
|
|
|
-- TODO this doesn't handle out-of-bounds exponents
|
|
function futil.math.to_float32(number)
|
|
if number == huge or number == -huge or number ~= number then
|
|
return number
|
|
end
|
|
local sign, significand, exponent = ("%a"):format(number):match("^(-?)0x([0-9a-f\\.]+)p([0-9+-]+)$")
|
|
return tonumber(("%s0x%sp%s"):format(sign, significand:sub(1, 8), exponent))
|
|
end
|