aboutsummaryrefslogtreecommitdiff
path: root/lib/core
diff options
context:
space:
mode:
authorBruce Hill <bruce@bruce-hill.com>2019-02-02 19:44:41 -0800
committerBruce Hill <bruce@bruce-hill.com>2019-02-02 19:44:41 -0800
commit8a01efc4e0c41beeeb27aaa87948877bb44b2529 (patch)
tree4de097f6380aff1c003b009c17fc9601e762d193 /lib/core
parentbe53f0c064b73fb2c6cf9f0aef97e75d97c84e07 (diff)
Added Range (1 to 3) and a bunch of tests for inverse dicts.
Diffstat (limited to 'lib/core')
-rw-r--r--lib/core/collections.nom100
1 files changed, 100 insertions, 0 deletions
diff --git a/lib/core/collections.nom b/lib/core/collections.nom
index dbe6900..9741faa 100644
--- a/lib/core/collections.nom
+++ b/lib/core/collections.nom
@@ -40,10 +40,42 @@ test:
assume [: for $k = $v in {.x = 1}: add {.key = $k, .value = $v}] ==
[{.key = "x", .value = 1}]
assume ({.x = 1, .y = 1} + {.y = 10, .z = 10}) == {.x = 1, .y = 11, .z = 10}
+ assume ({.x = 1, .y = 1} - {.y = 10, .z = 10}) == {.x = 1, .y = -9, .z = -10}
assume ({.x = 1, .y = 1} | {.y = 10, .z = 10}) == {.x = 1, .y = 1, .z = 10}
assume ({.x = 1, .y = 1} & {.y = 10, .z = 10}) == {.y = 1}
assume ({.x = 1, .y = 1} ~ {.y = 10, .z = 10}) == {.x = 1, .z = 10}
+ # Set compliments:
+ assume (~{.x}).y
+ assume ((~{.x}).x == (nil))
+ $sc = (~{.x, .y})
+ $sc.y = 99
+
+ # For now, whether $sc.y == 99 or $sc.y == (yes) is unspecified,
+ (but the actual behavior is (yes))
+ assume ($sc.y and (not $sc.x))
+ assume ($sc == ((~{.x, .y}) | {.y = 99}))
+
+ # Both sets:
+ assume (({.x, .y} & {.y, .z}) == {.y})
+ assume (({.x, .y} | {.y, .z}) == {.x, .y, .z})
+ assume (({.x, .y} ~ {.y, .z}) == {.z, .x})
+
+ # Mixed:
+ assume (({.x, .y} & (~{.y, .z})) == {.x})
+ assume (({.x, .y} | (~{.y, .z})) == (~{.z}))
+ assume (({.x, .y} ~ (~{.y, .z})) == (~{.x}))
+
+ # Mixed reversed:
+ assume (((~{.y, .z}) & {.x, .y}) == {.x})
+ assume (((~{.y, .z}) | {.x, .y}) == (~{.z}))
+ assume (((~{.y, .z}) ~ {.x, .y}) == (~{.x}))
+
+ # Both set compliments:
+ assume (((~{.x, .y}) & (~{.y, .z})) == (~{.x, .y, .z}))
+ assume (((~{.x, .y}) | (~{.y, .z})) == (~{.y}))
+ assume (((~{.x, .y}) ~ (~{.y, .z})) == {.x, .z})
+
test:
assume ((entries in {.x = 1}) == [{.key = "x", .value = 1}])
@@ -131,3 +163,71 @@ external:
$unique, add $
$seen.$ = (yes)
return $unique
+
+# Ranges:
+test:
+ $r = (3 to 5)
+ assume ($r.2 == 4)
+ assume ($r is "a Range")
+ assume ((1 to 10, backwards) == (10 to 1 by -1))
+ assume ((#(1 to 10 by 2)) == 5)
+ $visited = []
+ for $ in (1 to 10 by 2):
+ $visited, add $
+ assume ($visited == [1, 3, 5, 7, 9])
+ $r = (1 to 10 by 2)
+ $visited = []
+ for $ in $r:
+ $visited, add $
+ assume ($visited == [1, 3, 5, 7, 9])
+$(inext) = (=lua "ipairs({})")
+$range_mt = {
+ .__type = "a Range"
+ .__index =
+ for ($self's $key):
+ if ($key is "a Number"):
+ if (($key % 1) != 0):
+ return (nil)
+ $i = ($self.first + ($key - 1) * $self.step)
+ if ($self.step > 0):
+ if ($i > $self.last):
+ return (nil)
+ ..else:
+ if ($i < $self.last):
+ return (nil)
+ return $i
+ return $range_mt.$key
+
+ .__len =
+ for $self:
+ $len = (($self.last - $self.first) / $self.step + 1)
+ if ($len < 0):
+ $len = 0
+ return ($len, rounded down)
+
+ .__eq =
+ for ($self == $other)
+ (($self's metatable) == ($other's metatable)) and
+ ($self.first == $other.first) and
+ ($self.last == $other.last) and ($self.step == $other.step)
+
+ .backwards = (for $self ($self.last to $self.first by (- $self.step)))
+ .__ipairs = (for $self: return $(inext) $self 0)
+ .as_text =
+ for $self:
+ if ($self.step == 1):
+ return "(\($self.first) to \($self.last))"
+ ..else:
+ return "(\($self.first) to \($self.last) by \($self.step))"
+}
+$range_mt.reversed = $range_mt.backwards
+$range_mt.__unm = $range_mt.backwards
+$range_mt.__tostring = $range_mt.as_text
+$range_mt.as_nomsu = $range_mt.as_text
+set $range_mt's metatable to (nil)
+external:
+ ($first to $last by $step) means
+ setmetatable {.first = $first, .last = $last, .step = $step} $range_mt
+
+ ($first to $last) means
+ setmetatable {.first = $first, .last = $last, .step = 1} $range_mt