aboutsummaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
-rw-r--r--bruijn.cabal2
-rw-r--r--std/List/Church.bruijn10
-rw-r--r--std/Number/Binary.bruijn2
-rw-r--r--std/Number/Ternary.bruijn2
-rw-r--r--std/Number/Unary.bruijn2
-rw-r--r--std/Set.bruijn18
-rw-r--r--std/Set/NumberSet.bruijn22
-rw-r--r--std/Set/StringSet.bruijn23
-rw-r--r--std/String.bruijn8
-rw-r--r--std/Tree/Balanced.bruijn17
10 files changed, 77 insertions, 29 deletions
diff --git a/bruijn.cabal b/bruijn.cabal
index 0938354..20cd3cd 100644
--- a/bruijn.cabal
+++ b/bruijn.cabal
@@ -58,6 +58,8 @@ data-files:
std/Number/Ternary.bruijn
std/Number/Unary.bruijn
std/Number/Wadsworth.bruijn
+ std/Set/NumberSet.bruijn
+ std/Set/StringSet.bruijn
std/Tree/Balanced.bruijn
std/Tree/Finger.bruijn
std/Tree/Rose.bruijn
diff --git a/std/List/Church.bruijn b/std/List/Church.bruijn
index c8d5d29..b48e7c8 100644
--- a/std/List/Church.bruijn
+++ b/std/List/Church.bruijn
@@ -421,13 +421,15 @@ eq? ⋀?‣ ∘∘∘ zip-with ⧗ (a → a → Boolean) → (List a) → Boolea
:test (eq? …=?… empty empty) (true)
# returns eq, lt, gt depending on comparison of two lists and comparison function
-compare-case z [[[[[[[rec]]]]]]] ⧗ (a → a → Boolean) → c → d → e → (List a) → (List a) → Boolean
- rec ∅?1 (∅?0 4 3) (∅?0 2 go)
- go [=?0 (7 6 5 4 3 ~2 ~1) 0] (5 ^1 ^0)
+compare-case' z [[[[[[[rec]]]]]]] ⧗ Compare → a → b → c → (List a) → (List a) → d
+ rec ∅?1 (∅?0 4 2) (∅?0 3 (5 eq gt lt ^1 ^0))
+ eq 6 5 4 3 2 ~1 ~0
+ gt 3
+ lt 2
# returns 1 if a>b, -1 if a<b and 0 if a=b
# also: spaceship operator
-compare [compare-case 0 (+0) (+1) (-1)] ⧗ (a → a → Boolean) → Binary → Binary → Number
+compare' [compare-case' 0 (+0) (+1) (-1)] ⧗ Compare → Binary → Binary → Number
# returns true if list is prefix of other list
prefix? z [[[[rec]]]] ⧗ (a → a → Boolean) → (List a) → (List a) → Boolean
diff --git a/std/Number/Binary.bruijn b/std/Number/Binary.bruijn
index 87f7312..c778890 100644
--- a/std/Number/Binary.bruijn
+++ b/std/Number/Binary.bruijn
@@ -139,6 +139,8 @@ binary→ternary [y [[[rec]]] [0] 0 (+0t)] ⧗ Binary → Ternary
# TODO: remove ternary conversion
compare-case [[[(T.compare-case 2 1 0) ⋔ binary→ternary]]] ⧗ a → b → c → Binary → Binary → d
+<?>‣ &compare-case
+
# returns true if number is greater than other number
# TODO: remove ternary conversion
gt? T.gt? ⋔ binary→ternary ⧗ Binary → Binary → Boolean
diff --git a/std/Number/Ternary.bruijn b/std/Number/Ternary.bruijn
index 5392b63..e00bbc5 100644
--- a/std/Number/Ternary.bruijn
+++ b/std/Number/Ternary.bruijn
@@ -291,6 +291,8 @@ gt? positive? ∘∘ sub ⧗ Number → Number → Boolean
compare-case [[[[[go (1 - 0)]]]]] ⧗ a → b → c → Number → Number → d
go [=?0 5 (>?0 4 3)]
+<?>‣ &compare-case
+
# ============================================================================ #
# most relevant functions are defined - we can now derive from Generic/Number! #
# ============================================================================ #
diff --git a/std/Number/Unary.bruijn b/std/Number/Unary.bruijn
index 214bfb9..96fef9a 100644
--- a/std/Number/Unary.bruijn
+++ b/std/Number/Unary.bruijn
@@ -103,6 +103,8 @@ eq? [[=?(1 - 0) ⋀? =?(0 - 1)]] ⧗ Unary → Unary → Boolean
compare-case [[[[[go (1 - 0) (0 - 1)]]]]] ⧗ a → b → c → Unary → Unary → d
go [[=?0 (=?1 6 5) 4]]
+<?>‣ &compare-case
+
# ============================================================================ #
# most relevant functions are defined - we can now derive from Generic/Number! #
# ============================================================================ #
diff --git a/std/Set.bruijn b/std/Set.bruijn
index bec1645..0b9ea6d 100644
--- a/std/Set.bruijn
+++ b/std/Set.bruijn
@@ -1,6 +1,6 @@
# MIT License, Copyright (c) 2023 Marvin Borner
-# Set implementation using AVL trees
-# can currently only store Numbers (due to std/Tree/Balanced)
+# Generic set implementation using AVL trees
+# some functions require a compare-case argument!
:import std/Tree/Balanced T
:import std/List .
@@ -9,13 +9,10 @@
empty T.empty ⧗ Set
# adds a number of a set
-add T.insert ⧗ Number → Set → Set
+add T.insert ⧗ Compare → Number → Set → Set
# returns true if a number is in a set
-has? T.has? ⧗ Number → Set → Boolean
-
-:test (has? (+5) (add (+5) empty)) ([[1]])
-:test (has? (+5) empty) ([[0]])
+has? T.has? ⧗ Compare → Number → Set → Boolean
# count of elements in set
size T.size ⧗ Set → Number
@@ -24,9 +21,4 @@ size T.size ⧗ Set → Number
set→list T.tree→list ⧗ Set → (List Number)
# converts a list to a set
-list→set T.list→tree ⧗ (List Number) → Set
-
-:test (has? (+0) (list→set ((+5) : ((+3) : ((+2) : ((+1) : {}(+0))))))) ([[1]])
-:test (has? (+5) (list→set ((+5) : ((+3) : ((+2) : ((+1) : {}(+0))))))) ([[1]])
-:test (has? (+6) (list→set ((+5) : ((+3) : ((+2) : ((+1) : {}(+0))))))) ([[0]])
-:test (has? (+7) (list→set ((+5) : ((+7) : {}(+1))))) ([[1]])
+list→set T.list→tree ⧗ Compare → (List Number) → Set
diff --git a/std/Set/NumberSet.bruijn b/std/Set/NumberSet.bruijn
new file mode 100644
index 0000000..220e2dc
--- /dev/null
+++ b/std/Set/NumberSet.bruijn
@@ -0,0 +1,22 @@
+# MIT License, Copyright (c) 2024 Marvin Borner
+
+:input std/Set
+
+:import std/Number T
+
+# adds a number of a set
+add T.<?>add ⧗ Number → NumberSet → NumberSet
+
+# returns true if a number is in a set
+has? T.<?>has? ⧗ Number → NumberSet → Boolean
+
+:test (has? (+5) (add (+5) empty)) ([[1]])
+:test (has? (+5) empty) ([[0]])
+
+# converts a list to a set
+list→set T.<?>list→set ⧗ (List Number) → NumberSet
+
+:test (has? (+0) (list→set ((+5) : ((+3) : ((+2) : ((+1) : {}(+0))))))) ([[1]])
+:test (has? (+5) (list→set ((+5) : ((+3) : ((+2) : ((+1) : {}(+0))))))) ([[1]])
+:test (has? (+6) (list→set ((+5) : ((+3) : ((+2) : ((+1) : {}(+0))))))) ([[0]])
+:test (has? (+7) (list→set ((+5) : ((+7) : {}(+1))))) ([[1]])
diff --git a/std/Set/StringSet.bruijn b/std/Set/StringSet.bruijn
new file mode 100644
index 0000000..4bee345
--- /dev/null
+++ b/std/Set/StringSet.bruijn
@@ -0,0 +1,23 @@
+# MIT License, Copyright (c) 2024 Marvin Borner
+# TODO: hash instead of comparing
+
+:input std/Set
+
+:import std/String S
+
+# adds a number of a set
+add S.<?>add ⧗ String → StringSet → StringSet
+
+# returns true if a number is in a set
+has? S.<?>has? ⧗ String → StringSet → Boolean
+
+:test (has? "abc" (add "abc" empty)) ([[1]])
+:test (has? "abc" empty) ([[0]])
+
+# converts a list to a set
+list→set S.<?>list→set ⧗ (List String) → StringSet
+
+:test (has? "0" (list→set ("a" : ("b" : ("d" : ("c" : {}"0")))))) ([[1]])
+:test (has? "a" (list→set ("a" : ("b" : ("d" : ("c" : {}"0")))))) ([[1]])
+:test (has? "e" (list→set ("a" : ("b" : ("d" : ("c" : {}"0")))))) ([[0]])
+:test (has? "c" (list→set ("a" : ("c" : {}"b")))) ([[1]])
diff --git a/std/String.bruijn b/std/String.bruijn
index 291188d..4ee002b 100644
--- a/std/String.bruijn
+++ b/std/String.bruijn
@@ -18,7 +18,9 @@ eq? eq? B.eq? ⧗ String → String → Boolean
?‣ &eq?
# returns eq, gt, lt depending on comparison of two numbers
-compare-case B.<=>compare-case ⧗ a → b → c → String → String → d
+compare-case B.<?>compare-case' ⧗ a → b → c → String → String → d
+
+<?>‣ &compare-case
# returns 1 if a>b, -1 if a<b and 0 if a=b
# also: spaceship operator
@@ -31,8 +33,8 @@ compare compare-case (+0) (+1) (-1) ⧗ String → String → Number
:test (compare "2" "2") ((+0))
:test (compare "2" "1") ((+1))
:test (compare "1" "2") ((-1))
-:test (compare "12" "1") ((-1))
-:test (compare "1" "12") ((+1))
+:test (compare "12" "1") ((+1))
+:test (compare "1" "12") ((-1))
# returns true if string is lexically less than other string
lt? c-lt? ∘∘ compare ⧗ String → String → Boolean
diff --git a/std/Tree/Balanced.bruijn b/std/Tree/Balanced.bruijn
index 8fa3880..70e749e 100644
--- a/std/Tree/Balanced.bruijn
+++ b/std/Tree/Balanced.bruijn
@@ -1,6 +1,5 @@
# MIT License, Copyright (c) 2023 Marvin Borner
-# Balanced AVL tree for numerical leafs, inspired by Rudy Matela's implementation
-# TODO: Extend for arbitrary orderable types?
+# Balanced AVL tree, inspired by Rudy Matela's implementation
# TODO: Analyze performance bottlenecks
:import std/Combinator .
@@ -80,27 +79,27 @@ balance [go (factor 0)] ⧗ (Option BalancedTree) → (Option BalancedTree)
else 1
# inserts a number into a tree
-insert z [[[rec]]] ⧗ Number → (Option BalancedTree) → (Option BalancedTree)
+insert [z [[[rec]]]] ⧗ Compare → Number → (Option BalancedTree) → (Option BalancedTree)
rec none? 0 (some (leaf 1)) (balance (u 1 ?(!0)))
- u compare-case eq gt lt
+ u 3 eq gt lt
eq 0
gt some (node //(!0) ?(!0) (2 1 \\(!0)))
lt some (node (2 1 //(!0)) ?(!0) \\(!0))
# returns true if a number is in a tree
-has? z [[[rec]]] ⧗ Number → (Option BalancedTree) → Boolean
+has? [z [[[rec]]]] ⧗ Compare → Number → (Option BalancedTree) → Boolean
rec none? 0 false (u 1 ?(!0))
- u compare-case eq gt lt
+ u 3 eq gt lt
eq true
gt 2 1 \\(!0)
lt 2 1 //(!0)
-:test (has? (+42) empty) (false)
+:test (has? compare-case (+42) empty) (false)
# number of elements in tree (slow)
size z [[rec]] ⧗ (Option BalancedTree) → Number
rec none? 0 case-empty case-full
- case-full (1 //(!0)) + (1 \\(!0)) + (+1)
+ case-full ++((1 //(!0)) + (1 \\(!0)))
case-empty (+0)
# converts a tree to a list
@@ -108,4 +107,4 @@ tree→list z [[map-or L.empty go 0]] ⧗ (Option BalancedTree) → (List Number
go [L.append (L.append (2 //0) L.{}(?0)) (2 \\0)]
# converts a list to a tree
-list→tree L.foldr insert empty ⧗ (List Number) → (Option BalancedTree)
+list→tree [L.foldr (insert 0) empty] ⧗ Compare → (List Number) → (Option BalancedTree)