add gs
This commit is contained in:
+12
@@ -0,0 +1,12 @@
|
||||
--[[
|
||||
Defines utilities for working with 'dictionary-like' tables.
|
||||
|
||||
Dictionaries can be indexed by any value, but don't have the ordering
|
||||
expectations that lists have.
|
||||
]]
|
||||
|
||||
return {
|
||||
join = require(script.join),
|
||||
keys = require(script.keys),
|
||||
values = require(script.values),
|
||||
}
|
||||
+5
@@ -0,0 +1,5 @@
|
||||
return function()
|
||||
it("should load", function()
|
||||
require(script.Parent)
|
||||
end)
|
||||
end
|
||||
+30
@@ -0,0 +1,30 @@
|
||||
local None = require(script.Parent.Parent.None)
|
||||
|
||||
--[[
|
||||
Combine a number of dictionary-like tables into a new table.
|
||||
|
||||
Keys specified in later tables will overwrite keys in previous tables.
|
||||
|
||||
Use `Cryo.None` as a value to remove a key. This is necessary because
|
||||
Lua does not distinguish between a value not being present in a table and a
|
||||
value being `nil`.
|
||||
]]
|
||||
local function join(...)
|
||||
local new = {}
|
||||
|
||||
for i = 1, select("#", ...) do
|
||||
local source = select(i, ...)
|
||||
|
||||
for key, value in pairs(source) do
|
||||
if value == None then
|
||||
new[key] = nil
|
||||
else
|
||||
new[key] = value
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
return new
|
||||
end
|
||||
|
||||
return join
|
||||
+94
@@ -0,0 +1,94 @@
|
||||
return function()
|
||||
local join = require(script.Parent.join)
|
||||
local None = require(script.Parent.Parent.None)
|
||||
|
||||
it("should return a new table", function()
|
||||
local a = {}
|
||||
|
||||
expect(join(a)).never.to.equal(a)
|
||||
end)
|
||||
|
||||
it("should merge tables, overwriting previous values", function()
|
||||
local a = {
|
||||
foo = "foo-a",
|
||||
bar = "bar-a",
|
||||
}
|
||||
|
||||
local b = {
|
||||
foo = "foo-b",
|
||||
baz = "baz-b",
|
||||
}
|
||||
|
||||
local c = join(a, b)
|
||||
|
||||
expect(c.foo).to.equal(b.foo)
|
||||
expect(c.bar).to.equal(a.bar)
|
||||
expect(c.baz).to.equal(b.baz)
|
||||
end)
|
||||
|
||||
it("should remove values set to None", function()
|
||||
local a = {
|
||||
foo = "foo-a",
|
||||
}
|
||||
|
||||
local b = {
|
||||
foo = None,
|
||||
}
|
||||
|
||||
local c = join(a, b)
|
||||
|
||||
expect(c.foo).to.equal(nil)
|
||||
end)
|
||||
|
||||
it("should not mutate passed in tables", function()
|
||||
local mutationsA = 0
|
||||
local mutationsB = 0
|
||||
|
||||
local a = {}
|
||||
local b = {
|
||||
foo = "foo-b",
|
||||
}
|
||||
|
||||
setmetatable(a, {
|
||||
__newindex = function()
|
||||
mutationsA = mutationsA + 1
|
||||
end,
|
||||
})
|
||||
|
||||
setmetatable(b, {
|
||||
__newindex = function()
|
||||
mutationsB = mutationsB + 1
|
||||
end,
|
||||
})
|
||||
|
||||
join(a, b)
|
||||
|
||||
expect(mutationsA).to.equal(0)
|
||||
expect(mutationsB).to.equal(0)
|
||||
expect(b.foo).to.equal("foo-b")
|
||||
end)
|
||||
|
||||
it("should accept arbitrary numbers of tables", function()
|
||||
local a = {
|
||||
foo = "foo-a",
|
||||
}
|
||||
|
||||
local b = {
|
||||
bar = "bar-b",
|
||||
}
|
||||
|
||||
local c = {
|
||||
baz = "baz-c",
|
||||
}
|
||||
|
||||
local d = join(a, b, c)
|
||||
|
||||
expect(d.foo).to.equal(a.foo)
|
||||
expect(d.bar).to.equal(b.bar)
|
||||
expect(d.baz).to.equal(c.baz)
|
||||
end)
|
||||
|
||||
it("should accept zero tables", function()
|
||||
expect(join()).to.be.a("table")
|
||||
end)
|
||||
end
|
||||
+16
@@ -0,0 +1,16 @@
|
||||
--[[
|
||||
Returns a list of the keys from the given dictionary.
|
||||
]]
|
||||
local function keys(dictionary)
|
||||
local new = {}
|
||||
local index = 1
|
||||
|
||||
for key in pairs(dictionary) do
|
||||
new[index] = key
|
||||
index = index + 1
|
||||
end
|
||||
|
||||
return new
|
||||
end
|
||||
|
||||
return keys
|
||||
+74
@@ -0,0 +1,74 @@
|
||||
return function()
|
||||
local keys = require(script.Parent.keys)
|
||||
local None = require(script.Parent.Parent.None)
|
||||
|
||||
it("should not mutate the given table", function()
|
||||
local a = {
|
||||
Foo = "FooValue",
|
||||
Bar = "BarValue"
|
||||
}
|
||||
local aCopy = {
|
||||
Foo = "FooValue",
|
||||
Bar = "BarValue"
|
||||
}
|
||||
|
||||
keys(a)
|
||||
|
||||
for key, value in pairs(a) do
|
||||
expect(aCopy[key]).to.equal(value)
|
||||
end
|
||||
for key, value in pairs(aCopy) do
|
||||
expect(a[key]).to.equal(value)
|
||||
end
|
||||
end)
|
||||
|
||||
it("should return the correct keys", function()
|
||||
local a = {
|
||||
Foo = "FooValue",
|
||||
Bar = "BarValue",
|
||||
Test = "TestValue"
|
||||
}
|
||||
local keyCount = {
|
||||
Foo = 1,
|
||||
Bar = 1,
|
||||
Test = 1
|
||||
}
|
||||
local b = keys(a)
|
||||
|
||||
expect(#b).to.equal(3)
|
||||
for _, key in ipairs(b) do
|
||||
expect(keyCount[key]).never.to.equal(nil)
|
||||
keyCount[key] = keyCount[key] - 1
|
||||
end
|
||||
for _, count in pairs(keyCount) do
|
||||
expect(count).to.equal(0)
|
||||
end
|
||||
end)
|
||||
|
||||
it("should work with an empty table", function()
|
||||
local a = keys({})
|
||||
|
||||
expect(next(a)).to.equal(nil)
|
||||
end)
|
||||
|
||||
it("should contain a None element if there is a None key in the dictionary", function()
|
||||
local a = {
|
||||
[None] = "Foo",
|
||||
Bar = "BarValue"
|
||||
}
|
||||
local keyCount = {
|
||||
[None] = 1,
|
||||
Bar = 1
|
||||
}
|
||||
local b = keys(a)
|
||||
|
||||
expect(#b).to.equal(2)
|
||||
for _, key in ipairs(b) do
|
||||
expect(keyCount[key]).never.to.equal(nil)
|
||||
keyCount[key] = keyCount[key] - 1
|
||||
end
|
||||
for _, count in pairs(keyCount) do
|
||||
expect(count).to.equal(0)
|
||||
end
|
||||
end)
|
||||
end
|
||||
+17
@@ -0,0 +1,17 @@
|
||||
--[[
|
||||
Returns a list of the values of the given dictionary.
|
||||
]]
|
||||
|
||||
local function values(dictionary)
|
||||
local new = {}
|
||||
local index = 1
|
||||
|
||||
for _, value in pairs(dictionary) do
|
||||
new[index] = value
|
||||
index = index + 1
|
||||
end
|
||||
|
||||
return new
|
||||
end
|
||||
|
||||
return values
|
||||
+96
@@ -0,0 +1,96 @@
|
||||
return function()
|
||||
local values = require(script.Parent.values)
|
||||
local None = require(script.Parent.Parent.None)
|
||||
|
||||
it("should not mutate the given table", function()
|
||||
local a = {
|
||||
Foo = "FooValue",
|
||||
Bar = "BarValue"
|
||||
}
|
||||
local aCopy = {
|
||||
Foo = "FooValue",
|
||||
Bar = "BarValue"
|
||||
}
|
||||
|
||||
values(a)
|
||||
|
||||
for key, value in pairs(a) do
|
||||
expect(aCopy[key]).to.equal(value)
|
||||
end
|
||||
for key, value in pairs(aCopy) do
|
||||
expect(a[key]).to.equal(value)
|
||||
end
|
||||
end)
|
||||
|
||||
it("should return the correct values", function()
|
||||
local a = {
|
||||
Foo = "FooValue",
|
||||
Bar = "BarValue",
|
||||
Test = "TestValue"
|
||||
}
|
||||
local valueCount = {
|
||||
FooValue = 1,
|
||||
BarValue = 1,
|
||||
TestValue = 1
|
||||
}
|
||||
local b = values(a)
|
||||
|
||||
expect(#b).to.equal(3)
|
||||
for _, value in ipairs(b) do
|
||||
expect(valueCount[value]).never.to.equal(nil)
|
||||
valueCount[value] = valueCount[value] - 1
|
||||
end
|
||||
for _, count in pairs(valueCount) do
|
||||
expect(count).to.equal(0)
|
||||
end
|
||||
end)
|
||||
|
||||
it("should return duplicates if two values are the same", function()
|
||||
local a = {
|
||||
Foo = "FooValue",
|
||||
Bar = "BarValue",
|
||||
Test = "FooValue"
|
||||
}
|
||||
local valueCount = {
|
||||
FooValue = 2,
|
||||
BarValue = 1,
|
||||
}
|
||||
local b = values(a)
|
||||
|
||||
expect(#b).to.equal(3)
|
||||
for _, value in ipairs(b) do
|
||||
expect(valueCount[value]).never.to.equal(nil)
|
||||
valueCount[value] = valueCount[value] - 1
|
||||
end
|
||||
for _, count in pairs(valueCount) do
|
||||
expect(count).to.equal(0)
|
||||
end
|
||||
end)
|
||||
|
||||
it("should work with an empty table", function()
|
||||
local a = values({})
|
||||
|
||||
expect(next(a)).to.equal(nil)
|
||||
end)
|
||||
|
||||
it("should contain a None element if there is a None value in the dictionary", function()
|
||||
local a = {
|
||||
Foo = None,
|
||||
Bar = "BarValue"
|
||||
}
|
||||
local valueCount = {
|
||||
[None] = 1,
|
||||
BarValue = 1
|
||||
}
|
||||
local b = values(a)
|
||||
|
||||
expect(#b).to.equal(2)
|
||||
for _, value in ipairs(b) do
|
||||
expect(valueCount[value]).never.to.equal(nil)
|
||||
valueCount[value] = valueCount[value] - 1
|
||||
end
|
||||
for _, count in pairs(valueCount) do
|
||||
expect(count).to.equal(0)
|
||||
end
|
||||
end)
|
||||
end
|
||||
+20
@@ -0,0 +1,20 @@
|
||||
--[[
|
||||
Create a copy of a list with only values for which `callback` returns true.
|
||||
Calls the callback with (value, index).
|
||||
]]
|
||||
local function filter(list, callback)
|
||||
local new = {}
|
||||
local index = 1
|
||||
|
||||
for i = 1, #list do
|
||||
local value = list[i]
|
||||
if callback(value, i) then
|
||||
new[index] = value
|
||||
index = index + 1
|
||||
end
|
||||
end
|
||||
|
||||
return new
|
||||
end
|
||||
|
||||
return filter
|
||||
+77
@@ -0,0 +1,77 @@
|
||||
return function()
|
||||
local filter = require(script.Parent.filter)
|
||||
|
||||
it("should call the callback for each element", function()
|
||||
local a = {
|
||||
"foo1",
|
||||
"foo2",
|
||||
"foo3"
|
||||
}
|
||||
local copy = {}
|
||||
local function copyCallback(value, index)
|
||||
copy[index] = value
|
||||
return true
|
||||
end
|
||||
filter(a, copyCallback)
|
||||
|
||||
for key, value in pairs(a) do
|
||||
expect(copy[key]).to.equal(value)
|
||||
end
|
||||
|
||||
for key, value in pairs(copy) do
|
||||
expect(value).to.equal(a[key])
|
||||
end
|
||||
end)
|
||||
|
||||
it("should correctly use the filter callback", function()
|
||||
local a = {1, 2, 3, 4, 5}
|
||||
local function evenOnly(value)
|
||||
return value % 2 == 0
|
||||
end
|
||||
local b = filter(a, evenOnly)
|
||||
|
||||
expect(#b).to.equal(2)
|
||||
expect(b[1]).to.equal(2)
|
||||
expect(b[2]).to.equal(4)
|
||||
end)
|
||||
|
||||
it("should copy the list correctly", function()
|
||||
local a = {1, 2, 3}
|
||||
local function keepAll()
|
||||
return true
|
||||
end
|
||||
local b = filter(a, keepAll)
|
||||
|
||||
expect(b).never.to.equal(a)
|
||||
|
||||
for key, value in pairs(a) do
|
||||
expect(b[key]).to.equal(value)
|
||||
end
|
||||
|
||||
for key, value in pairs(b) do
|
||||
expect(value).to.equal(a[key])
|
||||
end
|
||||
end)
|
||||
|
||||
it("should work with an empty table", function()
|
||||
local called = false
|
||||
local function callback()
|
||||
called = true
|
||||
return true
|
||||
end
|
||||
local a = filter({}, callback)
|
||||
|
||||
expect(#a).to.equal(0)
|
||||
expect(called).to.equal(false)
|
||||
end)
|
||||
|
||||
it("should remove all element from a list when callback return always false", function()
|
||||
local a = {6, 2, 8, 6, 7}
|
||||
local function removeAll()
|
||||
return false
|
||||
end
|
||||
local b = filter(a, removeAll)
|
||||
|
||||
expect(#b).to.equal(0)
|
||||
end)
|
||||
end
|
||||
+23
@@ -0,0 +1,23 @@
|
||||
--[[
|
||||
Create a copy of a list doing a combination filter and map.
|
||||
|
||||
If callback returns nil for any item, it is considered filtered from the
|
||||
list. Any other value is considered the result of the 'map' operation.
|
||||
]]
|
||||
local function filterMap(list, callback)
|
||||
local new = {}
|
||||
local index = 1
|
||||
|
||||
for i = 1, #list do
|
||||
local result = callback(list[i], i)
|
||||
|
||||
if result ~= nil then
|
||||
new[index] = result
|
||||
index = index + 1
|
||||
end
|
||||
end
|
||||
|
||||
return new
|
||||
end
|
||||
|
||||
return filterMap
|
||||
+92
@@ -0,0 +1,92 @@
|
||||
return function()
|
||||
local filterMap = require(script.Parent.filterMap)
|
||||
|
||||
it("should return a new table", function()
|
||||
local a = {1, 2, 3}
|
||||
local function callback()
|
||||
return 1
|
||||
end
|
||||
local b = filterMap(a, callback)
|
||||
|
||||
expect(b).never.to.equal(a)
|
||||
end)
|
||||
|
||||
it("should call the callback for each element", function()
|
||||
local a = {
|
||||
"foo1",
|
||||
"foo2",
|
||||
"foo3"
|
||||
}
|
||||
local copy = {}
|
||||
local function callback(value, index)
|
||||
copy[index] = value
|
||||
return value
|
||||
end
|
||||
filterMap(a, callback)
|
||||
|
||||
for key, value in pairs(a) do
|
||||
expect(copy[key]).to.equal(value)
|
||||
end
|
||||
|
||||
for key, value in pairs(copy) do
|
||||
expect(value).to.equal(a[key])
|
||||
end
|
||||
end)
|
||||
|
||||
it("should correctly use the filter callback", function()
|
||||
local a = {1, 2, 3, 4, 5}
|
||||
local function doubleOddOnly(value)
|
||||
if value % 2 == 0 then
|
||||
return nil
|
||||
else
|
||||
return value * 2
|
||||
end
|
||||
end
|
||||
local b = filterMap(a, doubleOddOnly)
|
||||
|
||||
expect(#b).to.equal(3)
|
||||
expect(b[1]).to.equal(2)
|
||||
expect(b[2]).to.equal(6)
|
||||
expect(b[3]).to.equal(10)
|
||||
end)
|
||||
|
||||
it("should copy the list correctly", function()
|
||||
local a = {1, 2, 3}
|
||||
local function copyCallback(value)
|
||||
return value
|
||||
end
|
||||
local b = filterMap(a, copyCallback)
|
||||
|
||||
expect(b).never.to.equal(a)
|
||||
|
||||
for key, value in pairs(a) do
|
||||
expect(b[key]).to.equal(value)
|
||||
end
|
||||
|
||||
for key, value in pairs(b) do
|
||||
expect(value).to.equal(a[key])
|
||||
end
|
||||
end)
|
||||
|
||||
it("should work with an empty table", function()
|
||||
local called = false
|
||||
local function callback()
|
||||
called = true
|
||||
return true
|
||||
end
|
||||
local a = filterMap({}, callback)
|
||||
|
||||
expect(#a).to.equal(0)
|
||||
expect(called).to.equal(false)
|
||||
end)
|
||||
|
||||
it("should remove all elements from a list when callback return always nil", function()
|
||||
local a = {6, 2, 8, 6, 7}
|
||||
local function removeAll()
|
||||
return nil
|
||||
end
|
||||
local b = filterMap(a, removeAll)
|
||||
|
||||
expect(#b).to.equal(0)
|
||||
end)
|
||||
end
|
||||
+14
@@ -0,0 +1,14 @@
|
||||
--[[
|
||||
Returns the index of the first value found or nil if not found.
|
||||
]]
|
||||
|
||||
local function find(list, value)
|
||||
for i = 1, #list do
|
||||
if list[i] == value then
|
||||
return i
|
||||
end
|
||||
end
|
||||
return nil
|
||||
end
|
||||
|
||||
return find
|
||||
+30
@@ -0,0 +1,30 @@
|
||||
return function()
|
||||
local find = require(script.Parent.find)
|
||||
|
||||
it("should return the correct index", function()
|
||||
local a = {5, 4, 3, 2, 1}
|
||||
|
||||
expect(find(a, 1)).to.equal(5)
|
||||
expect(find(a, 2)).to.equal(4)
|
||||
expect(find(a, 3)).to.equal(3)
|
||||
expect(find(a, 4)).to.equal(2)
|
||||
expect(find(a, 5)).to.equal(1)
|
||||
end)
|
||||
|
||||
it("should work with an empty table", function()
|
||||
expect(find({}, 1)).to.equal(nil)
|
||||
end)
|
||||
|
||||
it("should return nil when the given value is not found", function()
|
||||
local a = {1, 2, 3}
|
||||
|
||||
expect(find(a, 4)).to.equal(nil)
|
||||
expect(type(find(a, 4))).to.equal("nil")
|
||||
end)
|
||||
|
||||
it("should return the index of the first value found", function()
|
||||
local list = {1, 2, 2}
|
||||
|
||||
expect(find(list, 2)).to.equal(2)
|
||||
end)
|
||||
end
|
||||
+14
@@ -0,0 +1,14 @@
|
||||
--[[
|
||||
Returns the index of the first value for which predicate(value, index) is truthy, or nil if not found.
|
||||
]]
|
||||
|
||||
local function findWhere(list, predicate)
|
||||
for i = 1, #list do
|
||||
if predicate(list[i], i) then
|
||||
return i
|
||||
end
|
||||
end
|
||||
return nil
|
||||
end
|
||||
|
||||
return findWhere
|
||||
+63
@@ -0,0 +1,63 @@
|
||||
return function()
|
||||
local findWhere = require(script.Parent.findWhere)
|
||||
|
||||
it("should return the correct index", function()
|
||||
local numbers = { 1, 5, 10, 7 }
|
||||
local isEven = function(value)
|
||||
return value % 2 == 0
|
||||
end
|
||||
|
||||
local isOdd = function(value)
|
||||
return value % 2 == 1
|
||||
end
|
||||
|
||||
expect(findWhere(numbers, isEven)).to.equal(3)
|
||||
expect(findWhere(numbers, isOdd)).to.equal(1)
|
||||
end)
|
||||
|
||||
it("should work with an empty table", function()
|
||||
local anything = function()
|
||||
return true
|
||||
end
|
||||
expect(findWhere({}, anything)).to.equal(nil)
|
||||
end)
|
||||
|
||||
it("should return nil when the when no value satisfies the predicate", function()
|
||||
local numbers = { 1, 2, 3 }
|
||||
local isFour = function(value)
|
||||
return value == 4
|
||||
end
|
||||
|
||||
expect(findWhere(numbers, isFour)).to.equal(nil)
|
||||
end)
|
||||
|
||||
it("should return the index of the first value for which the predicate is true", function()
|
||||
local list = { 1, 1, 1, 2, 2 }
|
||||
|
||||
local isTwo = function(value)
|
||||
return value == 2
|
||||
end
|
||||
|
||||
expect(findWhere(list, isTwo)).to.equal(4)
|
||||
end)
|
||||
|
||||
it("should allow access to table index in the predicate function", function()
|
||||
local list = { 5, 4, 3, 2, 1 }
|
||||
|
||||
local isIndexFour = function(_, index)
|
||||
return index == 4
|
||||
end
|
||||
|
||||
expect(findWhere(list, isIndexFour)).to.equal(4)
|
||||
end)
|
||||
|
||||
it("should allow access to both value and index in the predicate function", function()
|
||||
local list = { 1, 1, 2, 2, 1 }
|
||||
|
||||
local sumValueAndIndexToFive = function(value, index)
|
||||
return value + index == 5
|
||||
end
|
||||
|
||||
expect(findWhere(list, sumValueAndIndexToFive)).to.equal(3)
|
||||
end)
|
||||
end
|
||||
+14
@@ -0,0 +1,14 @@
|
||||
--[[
|
||||
Performs a left-fold of the list with the given initial value and callback.
|
||||
]]
|
||||
local function foldLeft(list, callback, initialValue)
|
||||
local accum = initialValue
|
||||
|
||||
for i = 1, #list do
|
||||
accum = callback(accum, list[i], i)
|
||||
end
|
||||
|
||||
return accum
|
||||
end
|
||||
|
||||
return foldLeft
|
||||
+61
@@ -0,0 +1,61 @@
|
||||
return function()
|
||||
local foldLeft = require(script.Parent.foldLeft)
|
||||
|
||||
it("should call the callback", function()
|
||||
local a = {1, 2, 3}
|
||||
local called = 0
|
||||
|
||||
foldLeft(a, function()
|
||||
called = called + 1
|
||||
end, 0)
|
||||
|
||||
expect(called).to.equal(3)
|
||||
end)
|
||||
|
||||
it("should not call the callback when the list is empty", function()
|
||||
local called = false
|
||||
|
||||
foldLeft({}, function()
|
||||
called = true
|
||||
end, 0)
|
||||
|
||||
expect(called).to.equal(false)
|
||||
end)
|
||||
|
||||
it("should call the callback for each element", function()
|
||||
local a = {4, 5, 6}
|
||||
local copy = {}
|
||||
|
||||
foldLeft(a, function(accum, value, index)
|
||||
copy[index] = value
|
||||
return accum
|
||||
end, 0)
|
||||
|
||||
expect(#copy).to.equal(#a)
|
||||
|
||||
for key, value in pairs(a) do
|
||||
expect(value).to.equal(copy[key])
|
||||
end
|
||||
end)
|
||||
|
||||
it("should pass the same modified initial value to the callback", function()
|
||||
local a = {5, 4, 3}
|
||||
local initialValue = {}
|
||||
|
||||
foldLeft(a, function(accum)
|
||||
expect(accum).to.equal(initialValue)
|
||||
return accum
|
||||
end, initialValue)
|
||||
end)
|
||||
|
||||
it("should call the callback in the correct order", function()
|
||||
local a = {5, 4, 3}
|
||||
local index = 1
|
||||
|
||||
foldLeft(a, function(accum, value)
|
||||
expect(value).to.equal(a[index])
|
||||
index = index + 1
|
||||
return accum
|
||||
end, 0)
|
||||
end)
|
||||
end
|
||||
+14
@@ -0,0 +1,14 @@
|
||||
--[[
|
||||
Performs a right-fold of the list with the given initial value and callback.
|
||||
]]
|
||||
local function foldRight(list, callback, initialValue)
|
||||
local accum = initialValue
|
||||
|
||||
for i = #list, 1, -1 do
|
||||
accum = callback(accum, list[i], i)
|
||||
end
|
||||
|
||||
return accum
|
||||
end
|
||||
|
||||
return foldRight
|
||||
+61
@@ -0,0 +1,61 @@
|
||||
return function()
|
||||
local foldRight = require(script.Parent.foldRight)
|
||||
|
||||
it("should call the callback", function()
|
||||
local a = {1, 2, 3}
|
||||
local called = 0
|
||||
|
||||
foldRight(a, function()
|
||||
called = called + 1
|
||||
end, 0)
|
||||
|
||||
expect(called).to.equal(3)
|
||||
end)
|
||||
|
||||
it("should not call the callback when the list is empty", function()
|
||||
local called = false
|
||||
|
||||
foldRight({}, function()
|
||||
called = true
|
||||
end, 0)
|
||||
|
||||
expect(called).to.equal(false)
|
||||
end)
|
||||
|
||||
it("should call the callback for each element", function()
|
||||
local a = {4, 5, 6}
|
||||
local copy = {}
|
||||
|
||||
foldRight(a, function(accum, value, index)
|
||||
copy[index] = value
|
||||
return accum
|
||||
end, 0)
|
||||
|
||||
expect(#copy).to.equal(#a)
|
||||
|
||||
for key, value in pairs(a) do
|
||||
expect(value).to.equal(copy[key])
|
||||
end
|
||||
end)
|
||||
|
||||
it("should pass the same modified initial value to the callback", function()
|
||||
local a = {5, 4, 3}
|
||||
local initialValue = {}
|
||||
|
||||
foldRight(a, function(accum)
|
||||
expect(accum).to.equal(initialValue)
|
||||
return accum
|
||||
end, initialValue)
|
||||
end)
|
||||
|
||||
it("should call the callback in the correct order", function()
|
||||
local a = {5, 4, 3}
|
||||
local index = 3
|
||||
|
||||
foldRight(a, function(accum, value)
|
||||
expect(value).to.equal(a[index])
|
||||
index = index - 1
|
||||
return accum
|
||||
end, 0)
|
||||
end)
|
||||
end
|
||||
+19
@@ -0,0 +1,19 @@
|
||||
--[[
|
||||
Returns a new list containing only the elements within the given range.
|
||||
]]
|
||||
|
||||
local function getRange(list, startIndex, endIndex)
|
||||
assert(startIndex <= endIndex, "startIndex must be less than or equal to endIndex")
|
||||
|
||||
local new = {}
|
||||
local index = 1
|
||||
|
||||
for i = math.max(1, startIndex), math.min(#list, endIndex) do
|
||||
new[index] = list[i]
|
||||
index = index + 1
|
||||
end
|
||||
|
||||
return new
|
||||
end
|
||||
|
||||
return getRange
|
||||
+62
@@ -0,0 +1,62 @@
|
||||
return function()
|
||||
local getRange = require(script.Parent.getRange)
|
||||
|
||||
it("should return the correct range", function()
|
||||
local a = {1, 2, 3, 4}
|
||||
local b = getRange(a, 2, 3)
|
||||
|
||||
expect(b[1]).to.equal(2)
|
||||
expect(b[2]).to.equal(3)
|
||||
expect(#b).to.equal(2)
|
||||
|
||||
local c = getRange(a, 4, 4)
|
||||
expect(#c).to.equal(1)
|
||||
expect(c[1]).to.equal(4)
|
||||
end)
|
||||
|
||||
it("should throw when the start index is higher than the end index", function()
|
||||
local a = {5, 8, 7, 2, 3, 7}
|
||||
|
||||
expect(function()
|
||||
getRange(a, 4, 1)
|
||||
end).to.throw()
|
||||
end)
|
||||
|
||||
it("should copy the table", function()
|
||||
local a = {6, 8, 1, 3, 7, 2}
|
||||
local b = getRange(a, 1, #a)
|
||||
|
||||
for key, value in pairs(a) do
|
||||
expect(b[key]).to.equal(value)
|
||||
end
|
||||
|
||||
for key, value in pairs(b) do
|
||||
expect(value).to.equal(a[key])
|
||||
end
|
||||
end)
|
||||
|
||||
it("should work with an empty table", function()
|
||||
local a = getRange({}, 1, 5)
|
||||
|
||||
expect(a).to.be.a("table")
|
||||
expect(#a).to.equal(0)
|
||||
end)
|
||||
|
||||
it("should work when the start index is smaller that 1", function()
|
||||
local a = {1, 2, 3, 4}
|
||||
local b = getRange(a, -2, 2)
|
||||
|
||||
expect(#b).to.equal(2)
|
||||
expect(b[1]).to.equal(1)
|
||||
expect(b[2]).to.equal(2)
|
||||
end)
|
||||
|
||||
it("should work when the end index is larger that the list length", function()
|
||||
local a = {1, 2, 3, 4}
|
||||
local b = getRange(a, 3, 18)
|
||||
|
||||
expect(#b).to.equal(2)
|
||||
expect(b[1]).to.equal(3)
|
||||
expect(b[2]).to.equal(4)
|
||||
end)
|
||||
end
|
||||
+22
@@ -0,0 +1,22 @@
|
||||
--[[
|
||||
Defines utilities for working with 'list-like' tables.
|
||||
]]
|
||||
|
||||
return {
|
||||
filter = require(script.filter),
|
||||
filterMap = require(script.filterMap),
|
||||
find = require(script.find),
|
||||
findWhere = require(script.findWhere),
|
||||
foldLeft = require(script.foldLeft),
|
||||
foldRight = require(script.foldRight),
|
||||
getRange = require(script.getRange),
|
||||
join = require(script.join),
|
||||
map = require(script.map),
|
||||
removeIndex = require(script.removeIndex),
|
||||
removeRange = require(script.removeRange),
|
||||
removeValue = require(script.removeValue),
|
||||
replaceIndex = require(script.replaceIndex),
|
||||
reverse = require(script.reverse),
|
||||
sort = require(script.sort),
|
||||
toSet = require(script.toSet),
|
||||
}
|
||||
+5
@@ -0,0 +1,5 @@
|
||||
return function()
|
||||
it("should load", function()
|
||||
require(script.Parent)
|
||||
end)
|
||||
end
|
||||
+25
@@ -0,0 +1,25 @@
|
||||
local None = require(script.Parent.Parent.None)
|
||||
|
||||
--[[
|
||||
Joins any number of lists together into a new list
|
||||
]]
|
||||
local function join(...)
|
||||
local new = {}
|
||||
|
||||
for listKey = 1, select("#", ...) do
|
||||
local list = select(listKey, ...)
|
||||
local len = #new
|
||||
|
||||
for itemKey = 1, #list do
|
||||
if list[itemKey] == None then
|
||||
len = len - 1
|
||||
else
|
||||
new[len + itemKey] = list[itemKey]
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
return new
|
||||
end
|
||||
|
||||
return join
|
||||
+44
@@ -0,0 +1,44 @@
|
||||
return function()
|
||||
local join = require(script.Parent.join)
|
||||
local None = require(script.Parent.Parent.None)
|
||||
|
||||
it("should return a new table", function()
|
||||
local a = {}
|
||||
|
||||
expect(join(a)).never.to.equal(a)
|
||||
end)
|
||||
|
||||
it("should remove elements equal to None", function()
|
||||
local a = {
|
||||
"foo-a"
|
||||
}
|
||||
|
||||
local b = {
|
||||
None,
|
||||
"foo-b"
|
||||
}
|
||||
|
||||
local c = join(a, b)
|
||||
|
||||
expect(c[1]).to.equal("foo-a")
|
||||
expect(c[2]).to.equal("foo-b")
|
||||
expect(c[3]).to.equal(nil)
|
||||
end)
|
||||
|
||||
it("should accept arbitrary numbers of tables", function()
|
||||
local a = {1}
|
||||
local b = {2}
|
||||
local c = {3}
|
||||
|
||||
local d = join(a, b, c)
|
||||
|
||||
expect(#d).to.equal(3)
|
||||
expect(d[1]).to.equal(1)
|
||||
expect(d[2]).to.equal(2)
|
||||
expect(d[3]).to.equal(3)
|
||||
end)
|
||||
|
||||
it("should accept zero tables", function()
|
||||
expect(join()).to.be.a("table")
|
||||
end)
|
||||
end
|
||||
@@ -0,0 +1,14 @@
|
||||
--[[
|
||||
Create a copy of a list where each value is transformed by `callback`
|
||||
]]
|
||||
local function map(list, callback)
|
||||
local new = {}
|
||||
|
||||
for i = 1, #list do
|
||||
new[i] = callback(list[i], i)
|
||||
end
|
||||
|
||||
return new
|
||||
end
|
||||
|
||||
return map
|
||||
+61
@@ -0,0 +1,61 @@
|
||||
return function()
|
||||
local map = require(script.Parent.map)
|
||||
|
||||
it("should return a new table", function()
|
||||
local a = {1, 2, 3}
|
||||
|
||||
expect(map(a, function() end)).never.to.equal(a)
|
||||
end)
|
||||
|
||||
it("should call the callback for each element", function()
|
||||
local a = {5, 6, 7}
|
||||
local copy = {}
|
||||
map(a, function(value, index)
|
||||
copy[index] = value
|
||||
return value
|
||||
end)
|
||||
|
||||
for key, value in pairs(a) do
|
||||
expect(copy[key]).to.equal(value)
|
||||
end
|
||||
|
||||
for key, value in pairs(copy) do
|
||||
expect(value).to.equal(a[key])
|
||||
end
|
||||
end)
|
||||
|
||||
it("should copy list", function()
|
||||
local a = {1, 2, 3}
|
||||
local b = map(a, function(value)
|
||||
return value
|
||||
end)
|
||||
|
||||
for key, value in pairs(a) do
|
||||
expect(b[key]).to.equal(value)
|
||||
end
|
||||
|
||||
for key, value in pairs(b) do
|
||||
expect(value).to.equal(a[key])
|
||||
end
|
||||
end)
|
||||
|
||||
it("should sets the new values to the result of the given callback", function()
|
||||
local a = {5, 6, 7}
|
||||
local b = map(a, function(value)
|
||||
return value * 2
|
||||
end)
|
||||
|
||||
expect(#b).to.equal(#a)
|
||||
for i = 1, #a do
|
||||
expect(b[i]).to.equal(a[i] * 2)
|
||||
end
|
||||
end)
|
||||
|
||||
it("should work with an empty list", function()
|
||||
local a = {}
|
||||
local b = map(a, function() end)
|
||||
|
||||
expect(b).to.be.a("table")
|
||||
expect(b).never.to.equal(a)
|
||||
end)
|
||||
end
|
||||
+19
@@ -0,0 +1,19 @@
|
||||
--[[
|
||||
Remove the element at the given index.
|
||||
]]
|
||||
local function removeIndex(list, index)
|
||||
local new = {}
|
||||
local removed = 0
|
||||
|
||||
for i = 1, #list do
|
||||
if i == index then
|
||||
removed = 1
|
||||
else
|
||||
new[i - removed] = list[i]
|
||||
end
|
||||
end
|
||||
|
||||
return new
|
||||
end
|
||||
|
||||
return removeIndex
|
||||
+53
@@ -0,0 +1,53 @@
|
||||
return function()
|
||||
local removeIndex = require(script.Parent.removeIndex)
|
||||
local None = require(script.Parent.Parent.None)
|
||||
|
||||
it("should remove the element at the given index", function()
|
||||
local a = {
|
||||
"first",
|
||||
"second",
|
||||
"third"
|
||||
}
|
||||
|
||||
local b = removeIndex(a, 2)
|
||||
|
||||
expect(#b).to.equal(2)
|
||||
expect(b[1]).to.equal("first")
|
||||
expect(b[2]).to.equal("third")
|
||||
end)
|
||||
|
||||
it("should not remove any element if index is out of bound", function()
|
||||
local a = {
|
||||
"first",
|
||||
"second",
|
||||
"third"
|
||||
}
|
||||
local b = removeIndex(a, 4)
|
||||
|
||||
expect(#b).to.equal(#a)
|
||||
for i = 1, #a do
|
||||
expect(b[i]).to.equal(a[i])
|
||||
end
|
||||
|
||||
local c = removeIndex(a, -2)
|
||||
|
||||
expect(#c).to.equal(#a)
|
||||
for i = 1, #a do
|
||||
expect(c[i]).to.equal(a[i])
|
||||
end
|
||||
end)
|
||||
|
||||
it("should work with a None element", function()
|
||||
local a = {
|
||||
"first",
|
||||
None,
|
||||
"third"
|
||||
}
|
||||
|
||||
local b = removeIndex(a, 1)
|
||||
|
||||
expect(#b).to.equal(2)
|
||||
expect(b[1]).to.equal(None)
|
||||
expect(b[2]).to.equal("third")
|
||||
end)
|
||||
end
|
||||
+23
@@ -0,0 +1,23 @@
|
||||
--[[
|
||||
Remove the range from the list starting from the index.
|
||||
]]
|
||||
local function removeRange(list, startIndex, endIndex)
|
||||
assert(startIndex <= endIndex, "startIndex must be less than or equal to endIndex")
|
||||
|
||||
local new = {}
|
||||
local index = 1
|
||||
|
||||
for i = 1, math.min(#list, startIndex - 1) do
|
||||
new[index] = list[i]
|
||||
index = index + 1
|
||||
end
|
||||
|
||||
for i = endIndex + 1, #list do
|
||||
new[index] = list[i]
|
||||
index = index + 1
|
||||
end
|
||||
|
||||
return new
|
||||
end
|
||||
|
||||
return removeRange
|
||||
+75
@@ -0,0 +1,75 @@
|
||||
return function()
|
||||
local removeRange = require(script.Parent.removeRange)
|
||||
local None = require(script.Parent.Parent.None)
|
||||
|
||||
it("should remove elements properly", function()
|
||||
local a = {1, 2, 3}
|
||||
local b = removeRange(a, 2, 2)
|
||||
|
||||
expect(#b).to.equal(2)
|
||||
expect(b[1]).to.equal(1)
|
||||
expect(b[2]).to.equal(3)
|
||||
|
||||
local c = {1, 2, 3, 4, 5, 6}
|
||||
local d = removeRange(c, 1, 4)
|
||||
|
||||
expect(#d).to.equal(2)
|
||||
expect(d[1]).to.equal(5)
|
||||
expect(d[2]).to.equal(6)
|
||||
|
||||
local e = removeRange(c, 2, 5)
|
||||
|
||||
expect(#e).to.equal(2)
|
||||
expect(e[1]).to.equal(1)
|
||||
expect(e[2]).to.equal(6)
|
||||
end)
|
||||
|
||||
it("should throw when the start index is higher than the end index", function()
|
||||
local a = {1, 2, 3}
|
||||
|
||||
expect(function()
|
||||
removeRange(a, 2, 0)
|
||||
end).to.throw()
|
||||
|
||||
expect(function()
|
||||
removeRange(a, 1, -1)
|
||||
end).to.throw()
|
||||
end)
|
||||
|
||||
it("should copy the table when then indexes are higher than the list length", function()
|
||||
local a = {1, 2, 3}
|
||||
local b = removeRange(a, 4, 7)
|
||||
|
||||
expect(#b).to.equal(3)
|
||||
expect(b[1]).to.equal(1)
|
||||
expect(b[2]).to.equal(2)
|
||||
expect(b[3]).to.equal(3)
|
||||
end)
|
||||
|
||||
it("should work when the start index is smaller than 1", function()
|
||||
local a = {1, 2, 3, 4}
|
||||
local b = removeRange(a, -5, 2)
|
||||
|
||||
expect(#b).to.equal(2)
|
||||
expect(b[1]).to.equal(3)
|
||||
expect(b[2]).to.equal(4)
|
||||
end)
|
||||
|
||||
it("should work when the end index is greater than the list length", function()
|
||||
local a = {1, 2, 3, 4}
|
||||
local b = removeRange(a, 3, 8)
|
||||
|
||||
expect(#b).to.equal(2)
|
||||
expect(b[1]).to.equal(1)
|
||||
expect(b[2]).to.equal(2)
|
||||
end)
|
||||
|
||||
it("should work with a None element", function()
|
||||
local a = {1, None, 3}
|
||||
local b = removeRange(a, 1, 1)
|
||||
|
||||
expect(#b).to.equal(2)
|
||||
expect(b[1]).to.equal(None)
|
||||
expect(b[2]).to.equal(3)
|
||||
end)
|
||||
end
|
||||
+18
@@ -0,0 +1,18 @@
|
||||
--[[
|
||||
Creates a new list that has no occurrences of the given value.
|
||||
]]
|
||||
local function removeValue(list, value)
|
||||
local new = {}
|
||||
local index = 1
|
||||
|
||||
for i = 1, #list do
|
||||
if list[i] ~= value then
|
||||
new[index] = list[i]
|
||||
index = index + 1
|
||||
end
|
||||
end
|
||||
|
||||
return new
|
||||
end
|
||||
|
||||
return removeValue
|
||||
+43
@@ -0,0 +1,43 @@
|
||||
return function()
|
||||
local removeValue = require(script.Parent.removeValue)
|
||||
local None = require(script.Parent.Parent.None)
|
||||
|
||||
it("should remove the given value", function()
|
||||
local a = {1, 4, 3}
|
||||
local b = removeValue(a, 4)
|
||||
|
||||
expect(b[1]).to.equal(1)
|
||||
expect(b[2]).to.equal(3)
|
||||
end)
|
||||
|
||||
it("should remove all occurences of the same given value", function()
|
||||
local a = {1, 2, 2, 3}
|
||||
local b = removeValue(a, 2)
|
||||
|
||||
expect(#b).to.equal(2)
|
||||
expect(b[1]).to.equal(1)
|
||||
expect(b[2]).to.equal(3)
|
||||
end)
|
||||
|
||||
it("should work with an empty list", function()
|
||||
local a = removeValue({}, 1)
|
||||
|
||||
expect(a).to.be.a("table")
|
||||
expect(#a).to.equal(0)
|
||||
end)
|
||||
|
||||
it("should work with a None element", function()
|
||||
local a = {1, 2, None, 3}
|
||||
local b = removeValue(a, 2)
|
||||
|
||||
expect(#b).to.equal(3)
|
||||
expect(b[1]).to.equal(1)
|
||||
expect(b[2]).to.equal(None)
|
||||
expect(b[3]).to.equal(3)
|
||||
|
||||
local c = removeValue(a, None)
|
||||
|
||||
expect(c[3]).to.equal(3)
|
||||
expect(#c).to.equal(3)
|
||||
end)
|
||||
end
|
||||
+22
@@ -0,0 +1,22 @@
|
||||
--[[
|
||||
Returns a new list with the new value replaced at the given index.
|
||||
]]
|
||||
|
||||
local function replaceIndex(list, index, value)
|
||||
local new = {}
|
||||
local len = #list
|
||||
|
||||
assert(index <= len, "index must be less or equal than the list length")
|
||||
|
||||
for i = 1, len do
|
||||
if i == index then
|
||||
new[i] = value
|
||||
else
|
||||
new[i] = list[i]
|
||||
end
|
||||
end
|
||||
|
||||
return new
|
||||
end
|
||||
|
||||
return replaceIndex
|
||||
+52
@@ -0,0 +1,52 @@
|
||||
return function()
|
||||
local replaceIndex = require(script.Parent.replaceIndex)
|
||||
|
||||
it("should return a new table", function()
|
||||
local list = {1, 2, 3}
|
||||
|
||||
expect(replaceIndex(list, 2, 0)).never.to.equal(list)
|
||||
end)
|
||||
|
||||
it("should not mutate the original list", function()
|
||||
local list = {false, "foo", 3}
|
||||
local value = {}
|
||||
replaceIndex(list, 2, value)
|
||||
|
||||
expect(#list).to.equal(3)
|
||||
expect(list[1]).to.equal(false)
|
||||
expect(list[2]).to.equal("foo")
|
||||
expect(list[3]).to.equal(3)
|
||||
end)
|
||||
|
||||
it("should replace the value at the given index", function()
|
||||
local list = {1, 2, 3}
|
||||
local value = {}
|
||||
local result = replaceIndex(list, 2, value)
|
||||
|
||||
expect(result[1]).to.equal(1)
|
||||
expect(result[2]).to.equal(value)
|
||||
expect(result[3]).to.equal(3)
|
||||
expect(next(result[2])).to.equal(nil)
|
||||
end)
|
||||
|
||||
it("should throw if the given index is higher than the list length", function()
|
||||
local list = {1}
|
||||
|
||||
expect(function()
|
||||
replaceIndex(list, #list + 1, {})
|
||||
end).to.throw()
|
||||
end)
|
||||
|
||||
it("should be able to replace to a falsy value", function()
|
||||
local tableElement = {}
|
||||
local list = {tableElement, false, "value", true}
|
||||
local newValue = false
|
||||
|
||||
local result = replaceIndex(list, 3, newValue)
|
||||
|
||||
expect(result[1]).to.equal(tableElement)
|
||||
expect(result[2]).to.equal(false)
|
||||
expect(result[3]).to.equal(newValue)
|
||||
expect(result[4]).to.equal(true)
|
||||
end)
|
||||
end
|
||||
+17
@@ -0,0 +1,17 @@
|
||||
--[[
|
||||
Returns a new list with the reversed order of the given list
|
||||
]]
|
||||
|
||||
local function reverse(list)
|
||||
local new = {}
|
||||
local len = #list
|
||||
local top = len + 1
|
||||
|
||||
for i = 1, len do
|
||||
new[i] = list[top - i]
|
||||
end
|
||||
|
||||
return new
|
||||
end
|
||||
|
||||
return reverse
|
||||
+46
@@ -0,0 +1,46 @@
|
||||
return function()
|
||||
local reverse = require(script.Parent.reverse)
|
||||
|
||||
it("should return a new table", function()
|
||||
local a = {1, 2, 3}
|
||||
|
||||
expect(reverse(a)).never.to.equal(a)
|
||||
end)
|
||||
|
||||
it("should not mutate the given table", function()
|
||||
local a = {1, 2, 3}
|
||||
reverse(a)
|
||||
|
||||
expect(#a).to.equal(3)
|
||||
expect(a[1]).to.equal(1)
|
||||
expect(a[2]).to.equal(2)
|
||||
expect(a[3]).to.equal(3)
|
||||
end)
|
||||
|
||||
it("should contain the same elements", function()
|
||||
local a = {
|
||||
"Foo",
|
||||
"Bar"
|
||||
}
|
||||
local aSet = {
|
||||
Foo = true,
|
||||
Bar = true
|
||||
}
|
||||
local b = reverse(a)
|
||||
|
||||
expect(#b).to.equal(2)
|
||||
for _, value in ipairs(b) do
|
||||
expect(aSet[value]).to.equal(true)
|
||||
end
|
||||
end)
|
||||
|
||||
it("should reverse the list", function()
|
||||
local a = {1, 2, 3, 4}
|
||||
local b = reverse(a)
|
||||
|
||||
expect(b[1]).to.equal(4)
|
||||
expect(b[2]).to.equal(3)
|
||||
expect(b[3]).to.equal(2)
|
||||
expect(b[4]).to.equal(1)
|
||||
end)
|
||||
end
|
||||
+18
@@ -0,0 +1,18 @@
|
||||
--[[
|
||||
Returns a new list, ordered with the given sort callback.
|
||||
If no callback is given, the default table.sort will be used.
|
||||
]]
|
||||
|
||||
local function sort(list, callback)
|
||||
local new = {}
|
||||
|
||||
for i = 1, #list do
|
||||
new[i] = list[i]
|
||||
end
|
||||
|
||||
table.sort(new, callback)
|
||||
|
||||
return new
|
||||
end
|
||||
|
||||
return sort
|
||||
+74
@@ -0,0 +1,74 @@
|
||||
return function()
|
||||
local sort = require(script.Parent.sort)
|
||||
|
||||
it("should return a new table", function()
|
||||
local a = {}
|
||||
|
||||
expect(sort(a)).never.to.equal(a)
|
||||
end)
|
||||
|
||||
it("should not mutate the given table", function()
|
||||
local a = {77, "foo", 2}
|
||||
local function order(first, second)
|
||||
return tostring(first) < tostring(second)
|
||||
end
|
||||
sort(a, order)
|
||||
|
||||
expect(#a).to.equal(3)
|
||||
expect(a[1]).to.equal(77)
|
||||
expect(a[2]).to.equal("foo")
|
||||
expect(a[3]).to.equal(2)
|
||||
end)
|
||||
|
||||
it("should contain the same elements from the given table", function()
|
||||
local a = {
|
||||
"Foo",
|
||||
"Bar",
|
||||
"Test"
|
||||
}
|
||||
local elementSet = {
|
||||
Foo = true,
|
||||
Bar = true,
|
||||
Test = true
|
||||
}
|
||||
local b = sort(a)
|
||||
|
||||
expect(#b).to.equal(3)
|
||||
for _, value in ipairs(b) do
|
||||
expect(elementSet[value]).to.equal(true)
|
||||
end
|
||||
end)
|
||||
|
||||
it("should sort with the default table.sort when no callback is given", function()
|
||||
local a = {4, 2, 5, 3, 1}
|
||||
local b = sort(a)
|
||||
|
||||
table.sort(a)
|
||||
|
||||
expect(#b).to.equal(#a)
|
||||
for i = 1, #a do
|
||||
expect(b[i]).to.equal(a[i])
|
||||
end
|
||||
end)
|
||||
|
||||
it("should sort with the given callback", function()
|
||||
local a = {1, 2, 5, 3, 4}
|
||||
local function order(first, second)
|
||||
return first > second
|
||||
end
|
||||
local b = sort(a, order)
|
||||
|
||||
table.sort(a, order)
|
||||
|
||||
expect(#b).to.equal(#a)
|
||||
for i = 1, #a do
|
||||
expect(b[i]).to.equal(a[i])
|
||||
end
|
||||
end)
|
||||
|
||||
it("should work with an empty table", function()
|
||||
local a = sort({})
|
||||
|
||||
expect(#a).to.equal(0)
|
||||
end)
|
||||
end
|
||||
+16
@@ -0,0 +1,16 @@
|
||||
--[[
|
||||
Create a dictionary where each value in the given list corresponds to a key
|
||||
in the dictionary with a value of true
|
||||
]]
|
||||
|
||||
local function toSet(list)
|
||||
local new = {}
|
||||
|
||||
for i = 1, #list do
|
||||
new[list[i]] = true
|
||||
end
|
||||
|
||||
return new
|
||||
end
|
||||
|
||||
return toSet
|
||||
+42
@@ -0,0 +1,42 @@
|
||||
return function()
|
||||
local toSet = require(script.Parent.toSet)
|
||||
|
||||
it("should return a new table", function()
|
||||
local a = {1, 2, 3}
|
||||
|
||||
expect(toSet(a)).never.to.equal(a)
|
||||
end)
|
||||
|
||||
it("should not mutate the given table", function()
|
||||
local a = {"a", "b", "c"}
|
||||
toSet(a)
|
||||
|
||||
for k, v in pairs(a) do
|
||||
if k == 1 then
|
||||
expect(v).to.equal("a")
|
||||
elseif k == 2 then
|
||||
expect(v).to.equal("b")
|
||||
elseif k == 3 then
|
||||
expect(v).to.equal("c")
|
||||
else
|
||||
error("Extra key was added to table a")
|
||||
end
|
||||
end
|
||||
end)
|
||||
|
||||
it("should have every value in a as a key mapped to true in b", function()
|
||||
local a = {1, 2, 3, "a", "b", "c"}
|
||||
local b = toSet(a)
|
||||
|
||||
expect(#b).to.equal(3)
|
||||
expect(b[1]).to.equal(true)
|
||||
expect(b[2]).to.equal(true)
|
||||
expect(b[3]).to.equal(true)
|
||||
|
||||
expect(b[4]).to.equal(nil)
|
||||
|
||||
expect(b["a"]).to.equal(true)
|
||||
expect(b["b"]).to.equal(true)
|
||||
expect(b["c"]).to.equal(true)
|
||||
end)
|
||||
end
|
||||
@@ -0,0 +1,15 @@
|
||||
--[[
|
||||
Represents a value that is intentionally present, but should be interpreted
|
||||
as `nil`.
|
||||
|
||||
Cryo.None is used by included utilities to make removing values more
|
||||
ergonomic.
|
||||
]]
|
||||
|
||||
local None = newproxy(true)
|
||||
|
||||
getmetatable(None).__tostring = function()
|
||||
return "Cryo.None"
|
||||
end
|
||||
|
||||
return None
|
||||
+14
@@ -0,0 +1,14 @@
|
||||
return function()
|
||||
local None = require(script.Parent.None)
|
||||
|
||||
it("should be a userdata", function()
|
||||
expect(None).to.be.a("userdata")
|
||||
end)
|
||||
|
||||
it("should have a nice string name", function()
|
||||
local coerced = tostring(None)
|
||||
|
||||
expect(coerced:find("^userdata: ")).never.to.be.ok()
|
||||
expect(coerced:find("None")).to.be.ok()
|
||||
end)
|
||||
end
|
||||
@@ -0,0 +1,6 @@
|
||||
return {
|
||||
Dictionary = require(script.Dictionary),
|
||||
List = require(script.List),
|
||||
isEmpty = require(script.isEmpty),
|
||||
None = require(script.None),
|
||||
}
|
||||
@@ -0,0 +1,5 @@
|
||||
return function()
|
||||
it("should load", function()
|
||||
require(script.Parent)
|
||||
end)
|
||||
end
|
||||
@@ -0,0 +1,5 @@
|
||||
local function isEmpty(object)
|
||||
return next(object) == nil
|
||||
end
|
||||
|
||||
return isEmpty
|
||||
@@ -0,0 +1,5 @@
|
||||
# Generated by Rotriever. Format subject to change in future releases.
|
||||
name = "roblox/cryo"
|
||||
version = "1.0.0"
|
||||
commit = "272caa8f3f3b3b29296b462f80b65cc9b1c92f1e"
|
||||
source = "url+https://github.com/roblox/cryo"
|
||||
Reference in New Issue
Block a user