From 7f21e727f18fd07c38086ee505107a55bba1e28d Mon Sep 17 00:00:00 2001 From: Jakub Chomiczewski <49335730+MinionJakub@users.noreply.github.com> Date: Wed, 19 Jun 2024 08:44:50 +0200 Subject: [PATCH 01/27] Ordered Map and Ordered Set First implementation of Ordered Map and Ordered Set --- lib/OrderedMap.fram | 315 ++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 315 insertions(+) create mode 100644 lib/OrderedMap.fram diff --git a/lib/OrderedMap.fram b/lib/OrderedMap.fram new file mode 100644 index 00000000..8ab8732a --- /dev/null +++ b/lib/OrderedMap.fram @@ -0,0 +1,315 @@ +let false = False +let true = True + +rec + data Color = Red | Black + data Tree Value = Leaf | Node of Color, Tree Value , Value , Tree Value +end + +method empty {X,self : Tree X} = Leaf + +let isEmpty tree = + match tree with + | Leaf => true + | _ => false + end + +method isEmpty {X, self : Tree X} = isEmpty self + +let id x = x + +let balance tree = + match tree with + | Node Black (Node Red (Node Red a x b) y c) z d => + Node Red (Node Black a x b) y (Node Black c z d) + | Node Black (Node Red a x (Node Red b y c)) z d => + Node Red (Node Black a x b) y (Node Black c z d) + | Node Black a x (Node Red (Node Red b y c) z d) => + Node Red (Node Black a x b) y (Node Black c z d) + | Node Black a x (Node Red b y (Node Red c z d)) => + Node Red (Node Black a x b) y (Node Black c z d) + | x => x +end + +let paintItBlack tree = + match tree with + | Node Red a x b => Node Black a x b + | _ => tree + end + +let repaint tree = + match tree with + | Node Red _ _ _ => (False,paintItBlack tree) + | _ => (True, tree) + end + +let chkDelL color tree = + match color,tree with + | (Red,Leaf) => (False,Leaf) + | (Black,Leaf) => (True,Leaf) + | (Black, Node Red Leaf x Leaf) => (False, Node Black Leaf x Leaf) + | _ => (False,tree) (*Impossible*) + end + +let balL krotka = + match krotka with + | (Black,Node Red (Node Red a x b) y c, z ,d) + => Node Red (Node Black a x b) y (Node Black c z d) + | (Black,Node Red a x (Node Black b y c), z,d) + => Node Red (Node Black a x b) y (Node Black c z d) + | (color,a,x,b) => Node color a x b + end + +let balR krotka = + match krotka with + | (Black,a,x,Node Red b y (Node Red c z d)) + => Node Red (Node Black a x b) y (Node Black c z d) + | (Black,a,x,Node Red (Node Red b y c) z d) + => Node Red (Node Black a x b) y (Node Black c z d) + | (color,a,x,b) => Node color a x b + end + +let balDelL krotka = + match krotka with + | (False,color,left,value,right) + => (False,Node color left value right) + | (True,Red,left,value,Node Red b y c) + => (False,balR (Black,left,value,Node Red b y c)) + | (True,Black,_,x,Leaf) + => (false,Node Black Leaf x Leaf) + | (True,Black,left,x,Node Black b y c) + => repaint (balR (Black,left,x,Node Red b y c)) + | (True,Black,_,x,Node Red Leaf y Leaf) + => (False, Node Black Leaf x (Node Red Leaf y Leaf)) + | (true,Black,a,x,Node Red (Node Black b y c) z d) + => (false, Node Black (balL (Black,Node Red a x b,y,c)) z d) + | (bf,color,a,x,b) + => (bf,Node color a x b) (*Impossible*) + end + +let rec delMin tree = + match tree with + | Node color Leaf value right => (Some value, chkDelL color right) + | Node color left value right => + let (min,(bf,newleft)) = delMin left + in (min,balDelL (bf,color,newleft,value,right)) + | Leaf => (None,(False,Leaf)) + end + +let deletMin tree = let (value,(_,newtree)) = delMin tree in (value,newtree) + +method deletMin {X,self : Tree X} = deletMin self + +let chkDelR color tree = + match color,tree with + | (Black,Leaf) => (true,Leaf) + | (Red,Leaf) => (false,Leaf) + | (Black,Node Red Leaf value Leaf) => + (false,Node Black Leaf value Leaf) + | _ => (False,tree) (*Impossible*) + end + +let balDelR krotka = + match krotka with + | (false,color,left,value,right) => (false, Node color left value right) + | (true,Red,Node Black a x b, value,right) + => (false, balL (Black,Node Red a x b,value,right)) + | (true,Black,Leaf,value,_) => (false,Node Black Leaf value Leaf) + | (true,Black,Node Black a x b,value,right) + => repaint (balL (Black,Node Red a x b,value,right)) + | (true, Black, Node Red Leaf x Leaf, value, right) + => (false,Node Black (Node Red Leaf x Leaf) value right) + | (true,Black, Node Red a x (Node Black b y c),value,right) + => (false, Node Black a x (balR (Black,b,y,Node Red c value right))) + | (bf,color,left,value,right) => (bf,Node color left value right) (*Impossible*) + end + +let rec delMax tree = + match tree with + | Node color left value Leaf => (Some value, chkDelR color left) + | Node color left value right + => let (min,(bf,newright)) = delMax right + in (min,balDelR(bf,color,left,value,newright)) + | Leaf => (None,(false,Leaf)) + end + +let deletMax tree = + let (min,(_,newtree)) = delMax tree + in (min,newtree) + +method deletMax {X, self : Tree X} = deletMax self + +let rec del elem tree lt = + match tree with + | Leaf => (false,Leaf) + | Node color left value right + => if lt elem value + then (let (done,newleft) = del elem left lt + in balDelL (done,color,newleft,value,right)) + else if lt value elem + then (let (done,newright) = del elem right lt + in balDelR (done,color,left,value,right)) + else if isEmpty left then chkDelL color right + else if isEmpty right then chkDelR color left + else (let (maks, (bf,newtree)) = delMax left in + match maks with + | Some v => balDelL (bf,color,newtree,v,right) + | None => balDelL(bf,color,newtree,elem,right) (*Impossible*) + end) + end + +let delete elem tree lt = let (_,solution) = del elem tree lt in solution + +method remove {X, self : Tree X} elem lt = delete elem self lt + +let insert tree elem lt = + let rec ins tree = + match tree with + | Leaf => Node Red Leaf elem Leaf + | Node color a y b => + if lt elem y then balance (Node color (ins a) y b) + else if lt y elem then balance (Node color a y (ins b)) + else Node color a y b + end + let y = ins tree + in match y with + | Node _ y a b => Node Black y a b + | Leaf => Leaf + end + +method add {X, self : Tree X} elem lt = insert self elem lt + +let toList tree = + let rec _toList tree acc = + match tree with + | Leaf => acc + | Node _ a y b => _toList a (y :: _toList b acc) + end + in _toList tree [] + +method toList {X , self : Tree X} = toList self + +let fromList {X} (lista : List X) lt = + let rec _fromList lista (acc : Tree X) = + match lista with + | x :: xs => _fromList xs (acc.add x lt) + | [] => acc + end + in _fromList lista Leaf + +let rec foldlRB fun acc from = + match from with + | Leaf => acc + | Node _ a y b => + let left = foldlRB fun acc a in + let middle = (fun y left) in + foldlRB fun middle b +end + +let rec foldrRB fun acc from = +match from with + | Leaf => acc + | Node _ a y b => + let right = foldlRB fun acc b in + let middle = (fun y right) in + foldlRB fun middle a +end + +method traversL {X, self : Tree X} fun acc = foldlRB fun acc self +method traversR {X, self : Tree X} fun acc = foldrRB fun acc self + +//TODO: better merge +let merge {X} (from : Tree X) (to : Tree X) lt = + foldlRB (fn x (y : Tree X) => y.add x lt) to from + +let rec member elem tree lt = + match tree with + | Leaf => False + | Node _ l v r => + if lt elem v then member elem l lt + else if lt v elem then member elem r lt + else True + end + + +method member {X, self : Tree X} elem lt = member elem self lt + + +let add lt tree key value = insert tree (key,value) lt +let join lt tree1 tree2 = merge tree1 tree2 lt +let rmVal lt key tree = match tree with + | Leaf => Leaf + | Node _ _ (_,v) _ => delete (key,v) tree lt +end + +let rec _find lt elem tree = + match tree with + | Leaf => None + | Node _ l v r => if lt elem v then _find lt elem l + else if lt v elem then _find lt elem r else Some v +end + +let find lt key tree = + match tree with + | Leaf => None + | Node _ l v r => let (_,a) = v in _find lt (key,a) tree +end + +let update lt tree key val = let x = rmVal lt key tree in +add lt x key val + +let fst (a,b) = a +let snd (a,b) = b + +data OrderedMap Key Val = Map of +{ + T + , empty : T + , method add : T -> Key -> Val -> [] T + , method join : T -> T -> [] T + , method isEmpty : T -> [] Bool + , method deleteElem : Key -> T -> [] T + , method toList : T -> [] List (Pair Key Val) + , method update : T -> Key -> Val -> [] T + , method deleteMax : T -> [] T + , method deleteMin : T -> [] T +} + +pub let make {Key} {Val} (lt : Key -> [] Key -> [] Bool)= +Map { + T = Tree (Pair Key Val) + , empty = Leaf + , method add = add (fn (a,b) (c,d) => lt a c) + , method join = join (fn (a,b) (c,d) => lt a c) + , method isEmpty = isEmpty + , method deleteElem = rmVal (fn (a,b) (c,d) => lt a c) + , method toList = toList + , method update = update (fn (a,_) (key,_) => lt a key) + , method deleteMax = fn mapa => snd (deletMax mapa) + , method deleteMin = fn mapa => snd (deletMin mapa) +} + +data OrderedSet Value = Set of { + T + , empty : T + , method insert : T -> Value -> [] T + , method singleton : Value -> [] T + , method remove : Value -> T -> [] T + , method union : T -> T -> [] T + , method find : Value -> T -> [] Option Value + , method deleteMax : T -> [] T + , method deleteMin : T -> [] T +} + +pub let make {Value} (lt : Value -> [] Value -> [] Bool) = +Set { + T = Tree Value + , empty = Leaf + , method insert = fn tree elem => insert tree elem lt + , method singleton = fn elem => insert Leaf elem lt + , method remove = fn elem tree => delete elem tree lt + , method union = join lt + , method find = _find lt + , method deleteMax = fn mapa => snd (deletMax mapa) + , method deleteMin = fn mapa => snd (deletMin mapa) +} \ No newline at end of file From 4d6a53ad31cfdc4a11808c184a8d1e8ed79f08bc Mon Sep 17 00:00:00 2001 From: Jakub Chomiczewski <49335730+MinionJakub@users.noreply.github.com> Date: Thu, 20 Jun 2024 12:11:02 +0200 Subject: [PATCH 02/27] Update OrderedMap.fram Small changes to address my mistakes in naming. --- lib/OrderedMap.fram | 93 ++++++++++++++++++++++----------------------- 1 file changed, 45 insertions(+), 48 deletions(-) diff --git a/lib/OrderedMap.fram b/lib/OrderedMap.fram index 8ab8732a..dbeac005 100644 --- a/lib/OrderedMap.fram +++ b/lib/OrderedMap.fram @@ -1,6 +1,3 @@ -let false = False -let true = True - rec data Color = Red | Black data Tree Value = Leaf | Node of Color, Tree Value , Value , Tree Value @@ -10,8 +7,8 @@ method empty {X,self : Tree X} = Leaf let isEmpty tree = match tree with - | Leaf => true - | _ => false + | Leaf => True + | _ => False end method isEmpty {X, self : Tree X} = isEmpty self @@ -43,7 +40,7 @@ let repaint tree = | _ => (True, tree) end -let chkDelL color tree = +let checkDeleteLeft color tree = match color,tree with | (Red,Leaf) => (False,Leaf) | (Black,Leaf) => (True,Leaf) @@ -51,8 +48,8 @@ let chkDelL color tree = | _ => (False,tree) (*Impossible*) end -let balL krotka = - match krotka with +let repairLeft tuple = + match tuple with | (Black,Node Red (Node Red a x b) y c, z ,d) => Node Red (Node Black a x b) y (Node Black c z d) | (Black,Node Red a x (Node Black b y c), z,d) @@ -60,8 +57,8 @@ let balL krotka = | (color,a,x,b) => Node color a x b end -let balR krotka = - match krotka with +let repairRight tuple = + match tuple with | (Black,a,x,Node Red b y (Node Red c z d)) => Node Red (Node Black a x b) y (Node Black c z d) | (Black,a,x,Node Red (Node Red b y c) z d) @@ -69,30 +66,30 @@ let balR krotka = | (color,a,x,b) => Node color a x b end -let balDelL krotka = - match krotka with +let repairAfterDeleteLeft tuple = + match tuple with | (False,color,left,value,right) => (False,Node color left value right) | (True,Red,left,value,Node Red b y c) - => (False,balR (Black,left,value,Node Red b y c)) + => (False,repairRight (Black,left,value,Node Red b y c)) | (True,Black,_,x,Leaf) - => (false,Node Black Leaf x Leaf) + => (False,Node Black Leaf x Leaf) | (True,Black,left,x,Node Black b y c) - => repaint (balR (Black,left,x,Node Red b y c)) + => repaint (repairRight (Black,left,x,Node Red b y c)) | (True,Black,_,x,Node Red Leaf y Leaf) => (False, Node Black Leaf x (Node Red Leaf y Leaf)) - | (true,Black,a,x,Node Red (Node Black b y c) z d) - => (false, Node Black (balL (Black,Node Red a x b,y,c)) z d) + | (True,Black,a,x,Node Red (Node Black b y c) z d) + => (False, Node Black (repairLeft (Black,Node Red a x b,y,c)) z d) | (bf,color,a,x,b) => (bf,Node color a x b) (*Impossible*) end let rec delMin tree = match tree with - | Node color Leaf value right => (Some value, chkDelL color right) + | Node color Leaf value right => (Some value, checkDeleteLeft color right) | Node color left value right => let (min,(bf,newleft)) = delMin left - in (min,balDelL (bf,color,newleft,value,right)) + in (min,repairAfterDeleteLeft (bf,color,newleft,value,right)) | Leaf => (None,(False,Leaf)) end @@ -100,37 +97,37 @@ let deletMin tree = let (value,(_,newtree)) = delMin tree in (value,newtree) method deletMin {X,self : Tree X} = deletMin self -let chkDelR color tree = +let checkDeleteRight color tree = match color,tree with - | (Black,Leaf) => (true,Leaf) - | (Red,Leaf) => (false,Leaf) + | (Black,Leaf) => (True,Leaf) + | (Red,Leaf) => (False,Leaf) | (Black,Node Red Leaf value Leaf) => - (false,Node Black Leaf value Leaf) + (False,Node Black Leaf value Leaf) | _ => (False,tree) (*Impossible*) end -let balDelR krotka = - match krotka with - | (false,color,left,value,right) => (false, Node color left value right) - | (true,Red,Node Black a x b, value,right) - => (false, balL (Black,Node Red a x b,value,right)) - | (true,Black,Leaf,value,_) => (false,Node Black Leaf value Leaf) - | (true,Black,Node Black a x b,value,right) - => repaint (balL (Black,Node Red a x b,value,right)) - | (true, Black, Node Red Leaf x Leaf, value, right) - => (false,Node Black (Node Red Leaf x Leaf) value right) - | (true,Black, Node Red a x (Node Black b y c),value,right) - => (false, Node Black a x (balR (Black,b,y,Node Red c value right))) +let repairAfterDeleteRight tuple = + match tuple with + | (False,color,left,value,right) => (False, Node color left value right) + | (True,Red,Node Black a x b, value,right) + => (False, repairLeft (Black,Node Red a x b,value,right)) + | (True,Black,Leaf,value,_) => (False,Node Black Leaf value Leaf) + | (True,Black,Node Black a x b,value,right) + => repaint (repairLeft (Black,Node Red a x b,value,right)) + | (True, Black, Node Red Leaf x Leaf, value, right) + => (False,Node Black (Node Red Leaf x Leaf) value right) + | (True,Black, Node Red a x (Node Black b y c),value,right) + => (False, Node Black a x (repairRight (Black,b,y,Node Red c value right))) | (bf,color,left,value,right) => (bf,Node color left value right) (*Impossible*) end let rec delMax tree = match tree with - | Node color left value Leaf => (Some value, chkDelR color left) + | Node color left value Leaf => (Some value, checkDeleteRight color left) | Node color left value right => let (min,(bf,newright)) = delMax right - in (min,balDelR(bf,color,left,value,newright)) - | Leaf => (None,(false,Leaf)) + in (min,repairAfterDeleteRight(bf,color,left,value,newright)) + | Leaf => (None,(False,Leaf)) end let deletMax tree = @@ -141,20 +138,20 @@ method deletMax {X, self : Tree X} = deletMax self let rec del elem tree lt = match tree with - | Leaf => (false,Leaf) + | Leaf => (False,Leaf) | Node color left value right => if lt elem value then (let (done,newleft) = del elem left lt - in balDelL (done,color,newleft,value,right)) + in repairAfterDeleteLeft (done,color,newleft,value,right)) else if lt value elem then (let (done,newright) = del elem right lt - in balDelR (done,color,left,value,right)) - else if isEmpty left then chkDelL color right - else if isEmpty right then chkDelR color left + in repairAfterDeleteRight (done,color,left,value,right)) + else if isEmpty left then checkDeleteLeft color right + else if isEmpty right then checkDeleteRight color left else (let (maks, (bf,newtree)) = delMax left in match maks with - | Some v => balDelL (bf,color,newtree,v,right) - | None => balDelL(bf,color,newtree,elem,right) (*Impossible*) + | Some v => repairAfterDeleteLeft (bf,color,newtree,v,right) + | None => repairAfterDeleteLeft(bf,color,newtree,elem,right) (*Impossible*) end) end @@ -275,7 +272,7 @@ data OrderedMap Key Val = Map of , method deleteMin : T -> [] T } -pub let make {Key} {Val} (lt : Key -> [] Key -> [] Bool)= +pub let makeMap {Key, Val} (lt : Key -> [] Key -> [] Bool)= Map { T = Tree (Pair Key Val) , empty = Leaf @@ -301,7 +298,7 @@ data OrderedSet Value = Set of { , method deleteMin : T -> [] T } -pub let make {Value} (lt : Value -> [] Value -> [] Bool) = +pub let makeSet {Value} (lt : Value -> [] Value -> [] Bool) = Set { T = Tree Value , empty = Leaf @@ -312,4 +309,4 @@ Set { , method find = _find lt , method deleteMax = fn mapa => snd (deletMax mapa) , method deleteMin = fn mapa => snd (deletMin mapa) -} \ No newline at end of file +} From ef1d14f19b34ca0c88b6ab3bef90e9acbc6fc59e Mon Sep 17 00:00:00 2001 From: Jakub Chomiczewski <49335730+MinionJakub@users.noreply.github.com> Date: Fri, 21 Jun 2024 10:50:58 +0200 Subject: [PATCH 03/27] Implementation of Queues First implementation of queues based on implementation of Hood Melville queues from "Purely Functional Data Structures" Chris Okasaki. --- lib/Queue.fram | 125 +++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 125 insertions(+) create mode 100644 lib/Queue.fram diff --git a/lib/Queue.fram b/lib/Queue.fram new file mode 100644 index 00000000..d90a35dd --- /dev/null +++ b/lib/Queue.fram @@ -0,0 +1,125 @@ + +data MyInt = Zero | Positive of Int + +let addOne value = +match value with +| Zero => Positive 1 +| Positive n => Positive (n+1) +end + +let subOne value = +match value with +| Zero => Zero +| Positive n => if n == 1 then Zero else Positive (n-1) +end + +data RotationState Val = + | Idle + | Reversing of MyInt, List Val, List Val, List Val, List Val + | Appending of MyInt, List Val, List Val + | Done of List Val + +data HoodMelvilleQueue Val = + | HMQueue of MyInt, List Val, RotationState Val, MyInt, List Val + +let exec state = +match state with + | Reversing ok (x::f) f' (y::r) r' + => Reversing (addOne ok) f (x::f') r (y::r') + | Reversing ok [] f' [y] r' => Appending ok f' (y::r') + | Appending Zero f' r' => Done r' + | Appending ok (x::f') r' => Appending (subOne ok) f' (x::r') + | _ => state +end + +let invalidate state = +match state with + | Reversing ok f f' r r' => Reversing (subOne ok) f f' r r' + | Appending Zero f' (x::r') => Done r' + | Appending ok f' r' => Appending (subOne ok) f' r' + | _ => state +end + +let exec_twice hmqueue = +match hmqueue with +| HMQueue lenf f state lenr r +=> match exec (exec state) with + | Done newf => HMQueue lenf newf Idle lenr r + | newstate => HMQueue lenf f newstate lenr r + end +end + +let leq v1 v2 = +match (v1,v2) with +| (Zero,Zero) => True +| (Zero,Positive _) => True +| (Positive _, Zero) => False +| (Positive n, Positive m) => n <= m +end + +let add v1 v2 = +match (v1,v2) with +| (Zero,any) => any +| (any,Zero) => any +| (Positive n, Positive m) => Positive (n+m) +end + +let check queue = +match queue with +| HMQueue lenf f state lenr r +=> if leq lenr lenf then exec_twice queue +else ( + let newstate = Reversing Zero f [] r [] in + exec_twice (HMQueue (add lenf lenr) f newstate Zero []) +) +end + +let empty = HMQueue Zero [] Idle Zero [] +let isEmpty queue = +match queue with +| HMQueue Zero _ _ _ _ => True +| _ => False +end + +let snoc queue value = +match queue with +| HMQueue lenf f state lenr r => +check (HMQueue lenf f state (addOne lenr) (value :: r)) +end + +let head queue = +match queue with +| HMQueue Zero _ _ _ _ => None +| HMQueue _ (x::xs) _ _ _ => Some x +| _ => None // Impossible +end + +let tail queue = +match queue with +| HMQueue Zero _ _ _ _ => empty +| HMQueue _ [] _ _ _ => empty +| HMQueue lenf (x::xs) state lenr r => +check (HMQueue (subOne lenf) xs (invalidate state) lenr r) +end + +pub data Queue Val = Queue of { + T + , empty : T + , method isEmpty : T -> [] Bool + , method snoc : T -> Val -> [] T + , method tail : T -> [] T + , method push : T -> Val -> [] T + , method pop : T -> [] T + , method head : T -> [] Option Val +} + +pub let makeQueue {Val} = Queue { + T = HoodMelvilleQueue Val + , empty = empty + , method isEmpty = isEmpty + , method snoc = snoc + , method tail = tail + , method push = snoc + , method pop = tail + , method head = head +} \ No newline at end of file From 8bcd905e346d3a165f99de80294af6a054cbb72e Mon Sep 17 00:00:00 2001 From: Jakub Chomiczewski <49335730+MinionJakub@users.noreply.github.com> Date: Fri, 21 Jun 2024 10:52:44 +0200 Subject: [PATCH 04/27] Testing files for Map, Set, Queues. --- test/stdlib/stdlib0001_SetMap.fram | 19 +++++++++++++++++++ test/stdlib/stdlib0002_Queue.fram | 11 +++++++++++ 2 files changed, 30 insertions(+) create mode 100644 test/stdlib/stdlib0001_SetMap.fram create mode 100644 test/stdlib/stdlib0002_Queue.fram diff --git a/test/stdlib/stdlib0001_SetMap.fram b/test/stdlib/stdlib0001_SetMap.fram new file mode 100644 index 00000000..232cc070 --- /dev/null +++ b/test/stdlib/stdlib0001_SetMap.fram @@ -0,0 +1,19 @@ +import OrderedMap + +let lt (v1 : Int) (v2 : Int) = v1 < v2 + +let OrderedMap.Map {module StringMap} = OrderedMap.makeMap lt + +let x = StringMap.empty +let y = x.add 1 "Test 1" +let z = (y.isEmpty == False) && (x.isEmpty == True) +let g = y.deleteElem 1 + +let OrderedMap.Set {module IntSet} = OrderedMap.makeSet lt + +let x = IntSet.empty +let y = x.insert 1 +let z = y.insert 2 +let w = y.deleteMax +let g = w.isEmpty +let f = 5.singleton diff --git a/test/stdlib/stdlib0002_Queue.fram b/test/stdlib/stdlib0002_Queue.fram new file mode 100644 index 00000000..8428178f --- /dev/null +++ b/test/stdlib/stdlib0002_Queue.fram @@ -0,0 +1,11 @@ +import Queue + +let Queue.Queue {module IntQ} = Queue.makeQueue + +let x = IntQ.empty +let _ = if x.isEmpty then 1 else 0 +let y = x.push 1 +let w = y.head +let _ = if y.isEmpty then 1 else 0 +let z = y.pop +let _ = if z.isEmpty then 1 else 0 From 27ff11ed134e98dd607fb05ef0bf077742030760 Mon Sep 17 00:00:00 2001 From: Jakub Chomiczewski <49335730+MinionJakub@users.noreply.github.com> Date: Fri, 21 Jun 2024 10:55:17 +0200 Subject: [PATCH 05/27] Update OrderedMap.fram Little correction of definitions. --- lib/OrderedMap.fram | 60 +++++++++++++++++++++++++-------------------- 1 file changed, 34 insertions(+), 26 deletions(-) diff --git a/lib/OrderedMap.fram b/lib/OrderedMap.fram index dbeac005..6cea69e1 100644 --- a/lib/OrderedMap.fram +++ b/lib/OrderedMap.fram @@ -93,9 +93,9 @@ let rec delMin tree = | Leaf => (None,(False,Leaf)) end -let deletMin tree = let (value,(_,newtree)) = delMin tree in (value,newtree) +let deleteMin tree = let (value,(_,newtree)) = delMin tree in (value,newtree) -method deletMin {X,self : Tree X} = deletMin self +method deleteMin {X,self : Tree X} = deleteMin self let checkDeleteRight color tree = match color,tree with @@ -130,11 +130,11 @@ let rec delMax tree = | Leaf => (None,(False,Leaf)) end -let deletMax tree = +let deleteMax tree = let (min,(_,newtree)) = delMax tree in (min,newtree) -method deletMax {X, self : Tree X} = deletMax self +method deleteMax {X, self : Tree X} = deleteMax self let rec del elem tree lt = match tree with @@ -234,7 +234,7 @@ method member {X, self : Tree X} elem lt = member elem self lt let add lt tree key value = insert tree (key,value) lt let join lt tree1 tree2 = merge tree1 tree2 lt -let rmVal lt key tree = match tree with +let rmVal lt tree key = match tree with | Leaf => Leaf | Node _ _ (_,v) _ => delete (key,v) tree lt end @@ -246,32 +246,49 @@ let rec _find lt elem tree = else if lt v elem then _find lt elem r else Some v end -let find lt key tree = +//method find {X,self : Tree X} elem lt = _find lt elem self + +let find lt tree key = match tree with | Leaf => None | Node _ l v r => let (_,a) = v in _find lt (key,a) tree end -let update lt tree key val = let x = rmVal lt key tree in +let update lt tree key val = let x = rmVal lt tree key in add lt x key val let fst (a,b) = a let snd (a,b) = b -data OrderedMap Key Val = Map of +pub data OrderedMap Key Val = Map of { T , empty : T , method add : T -> Key -> Val -> [] T , method join : T -> T -> [] T , method isEmpty : T -> [] Bool - , method deleteElem : Key -> T -> [] T + , method deleteElem : T -> Key -> [] T , method toList : T -> [] List (Pair Key Val) , method update : T -> Key -> Val -> [] T , method deleteMax : T -> [] T , method deleteMin : T -> [] T + , method find : T -> Key -> [] Option (Pair Key Val) +} + +pub data OrderedSet Value = Set of { + T + , empty : T + , method isEmpty : T -> [] Bool + , method insert : T -> Value -> [] T + , method singleton : Value -> [] T + , method remove : T -> Value ->[] T + , method union : T -> T -> [] T + , method find : T -> Value -> [] Bool + , method deleteMax : T -> [] T + , method deleteMin : T -> [] T } + pub let makeMap {Key, Val} (lt : Key -> [] Key -> [] Bool)= Map { T = Tree (Pair Key Val) @@ -282,31 +299,22 @@ Map { , method deleteElem = rmVal (fn (a,b) (c,d) => lt a c) , method toList = toList , method update = update (fn (a,_) (key,_) => lt a key) - , method deleteMax = fn mapa => snd (deletMax mapa) - , method deleteMin = fn mapa => snd (deletMin mapa) + , method deleteMax = fn mapa => snd (deleteMax mapa) + , method deleteMin = fn mapa => snd (deleteMin mapa) + , method find = find (fn (a,b) (c,d) => lt a c) } -data OrderedSet Value = Set of { - T - , empty : T - , method insert : T -> Value -> [] T - , method singleton : Value -> [] T - , method remove : Value -> T -> [] T - , method union : T -> T -> [] T - , method find : Value -> T -> [] Option Value - , method deleteMax : T -> [] T - , method deleteMin : T -> [] T -} pub let makeSet {Value} (lt : Value -> [] Value -> [] Bool) = Set { T = Tree Value , empty = Leaf + , method isEmpty = isEmpty , method insert = fn tree elem => insert tree elem lt , method singleton = fn elem => insert Leaf elem lt - , method remove = fn elem tree => delete elem tree lt + , method remove = fn tree elem => delete elem tree lt , method union = join lt - , method find = _find lt - , method deleteMax = fn mapa => snd (deletMax mapa) - , method deleteMin = fn mapa => snd (deletMin mapa) + , method find = fn tree elem => member elem tree lt + , method deleteMax = fn mapa => snd (deleteMax mapa) + , method deleteMin = fn mapa => snd (deleteMin mapa) } From dae76bc5e8ee8d04e3c0f510e600b49d78e34f4c Mon Sep 17 00:00:00 2001 From: Jakub Chomiczewski Date: Wed, 14 Aug 2024 09:15:48 +0200 Subject: [PATCH 06/27] Changes to implementation and tests --- lib/OrderedMap.fram | 498 +++++++++++++---------------- lib/Queue.fram | 60 ++-- test/stdlib/stdlib0001_SetMap.fram | 19 -- test/stdlib/stdlib0002_Queue.fram | 11 - 4 files changed, 240 insertions(+), 348 deletions(-) delete mode 100644 test/stdlib/stdlib0001_SetMap.fram delete mode 100644 test/stdlib/stdlib0002_Queue.fram diff --git a/lib/OrderedMap.fram b/lib/OrderedMap.fram index 6cea69e1..bc658d68 100644 --- a/lib/OrderedMap.fram +++ b/lib/OrderedMap.fram @@ -1,320 +1,252 @@ -rec - data Color = Red | Black - data Tree Value = Leaf | Node of Color, Tree Value , Value , Tree Value -end +(* This file is part of DBL, released under MIT license. + * See LICENSE for details. +*) -method empty {X,self : Tree X} = Leaf +import open RedBlackTree +import open OrderedMapSignature -let isEmpty tree = +let rec member compare tree key = match tree with - | Leaf => True - | _ => False + | Leaf => False + | Node _ _ left (key',_) right => + match compare key key' with + | Less => member compare left key + | Equal => True + | Greater => member compare right key + end end -method isEmpty {X, self : Tree X} = isEmpty self - -let id x = x +let rec find compare tree key = + match tree with + | Leaf => None + | Node _ _ left (key', val) right => + match compare key key' with + | Less => find compare left key + | Equal => Some val + | Greater => find compare right key + end + end -let balance tree = - match tree with - | Node Black (Node Red (Node Red a x b) y c) z d => - Node Red (Node Black a x b) y (Node Black c z d) - | Node Black (Node Red a x (Node Red b y c)) z d => - Node Red (Node Black a x b) y (Node Black c z d) - | Node Black a x (Node Red (Node Red b y c) z d) => - Node Red (Node Black a x b) y (Node Black c z d) - | Node Black a x (Node Red b y (Node Red c z d)) => - Node Red (Node Black a x b) y (Node Black c z d) - | x => x -end +let rec operate compare tree key absentf presentf = + match search (fn (key', _ ) => compare key key') tree [] with + | (Leaf, zipper) => match absentf () with + | None => (None,None, tree) + | Some x => (None,Some x, zipRed (key,x) Leaf Leaf zipper) + end + | (Node color bulk left (_, val) right, zipper) => + match presentf val with + | None => (Some val, None, delete color left right zipper) + | Some x => (Some val, Some x, zip + (Node color bulk left (key,x) right) zipper) + end + end -let paintItBlack tree = +let rec foldr func tree acc = match tree with - | Node Red a x b => Node Black a x b - | _ => tree + | Leaf => acc + | Node _ _ left (key, val) right => + let val_right = (foldr func right acc) in + let val_middle = (func key val val_right) in + foldr func left val_middle end -let repaint tree = +let rec foldl func tree acc = match tree with - | Node Red _ _ _ => (False,paintItBlack tree) - | _ => (True, tree) - end - -let checkDeleteLeft color tree = - match color,tree with - | (Red,Leaf) => (False,Leaf) - | (Black,Leaf) => (True,Leaf) - | (Black, Node Red Leaf x Leaf) => (False, Node Black Leaf x Leaf) - | _ => (False,tree) (*Impossible*) - end - -let repairLeft tuple = - match tuple with - | (Black,Node Red (Node Red a x b) y c, z ,d) - => Node Red (Node Black a x b) y (Node Black c z d) - | (Black,Node Red a x (Node Black b y c), z,d) - => Node Red (Node Black a x b) y (Node Black c z d) - | (color,a,x,b) => Node color a x b - end + | Leaf => acc + | Node _ _ left (key, val) right => + let val_left = (foldl func left acc) in + let val_middle = (func key val val_left) in + foldl func right val_middle + end -let repairRight tuple = - match tuple with - | (Black,a,x,Node Red b y (Node Red c z d)) - => Node Red (Node Black a x b) y (Node Black c z d) - | (Black,a,x,Node Red (Node Red b y c) z d) - => Node Red (Node Black a x b) y (Node Black c z d) - | (color,a,x,b) => Node color a x b +let rec map tree func = match tree with + | Leaf => Leaf + | Node color bulk left (key,value) right => + Node color bulk (map left func) (key,func value) (map right func) end -let repairAfterDeleteLeft tuple = - match tuple with - | (False,color,left,value,right) - => (False,Node color left value right) - | (True,Red,left,value,Node Red b y c) - => (False,repairRight (Black,left,value,Node Red b y c)) - | (True,Black,_,x,Leaf) - => (False,Node Black Leaf x Leaf) - | (True,Black,left,x,Node Black b y c) - => repaint (repairRight (Black,left,x,Node Red b y c)) - | (True,Black,_,x,Node Red Leaf y Leaf) - => (False, Node Black Leaf x (Node Red Leaf y Leaf)) - | (True,Black,a,x,Node Red (Node Black b y c) z d) - => (False, Node Black (repairLeft (Black,Node Red a x b,y,c)) z d) - | (bf,color,a,x,b) - => (bf,Node color a x b) (*Impossible*) +let rec map2 tree func = match tree with + | Leaf => Leaf + | Node color bulk left (key, _) right => + Node color bulk (map2 left func) (key, func key) (map2 right func) end -let rec delMin tree = - match tree with - | Node color Leaf value right => (Some value, checkDeleteLeft color right) - | Node color left value right => - let (min,(bf,newleft)) = delMin left - in (min,repairAfterDeleteLeft (bf,color,newleft,value,right)) - | Leaf => (None,(False,Leaf)) +let rec app tree func = match tree with + | Leaf => () + | Node _ _ left (key,value) right => + let _ = app left func in + let _ = func key value in + app right func end -let deleteMin tree = let (value,(_,newtree)) = delMin tree in (value,newtree) - -method deleteMin {X,self : Tree X} = deleteMin self - -let checkDeleteRight color tree = - match color,tree with - | (Black,Leaf) => (True,Leaf) - | (Red,Leaf) => (False,Leaf) - | (Black,Node Red Leaf value Leaf) => - (False,Node Black Leaf value Leaf) - | _ => (False,tree) (*Impossible*) +let rec union compare tree1 tree2 merge = + match tree1 with + | Leaf => tree2 + | Node _ _ left1 (key1,value1) right1 => + match tree2 with + | Leaf => tree1 + | _ => let (output,left2,right2) = + split (fn (key2,_) => compare key1 key2) tree2 + in let new_pair = match output with + | None => (key1,value1) + | Some (_,value2) => (key1, merge key1 value1 value2) + end in join_val new_pair (union compare left1 left2 merge) + (union compare right1 right2 merge) + end end -let repairAfterDeleteRight tuple = - match tuple with - | (False,color,left,value,right) => (False, Node color left value right) - | (True,Red,Node Black a x b, value,right) - => (False, repairLeft (Black,Node Red a x b,value,right)) - | (True,Black,Leaf,value,_) => (False,Node Black Leaf value Leaf) - | (True,Black,Node Black a x b,value,right) - => repaint (repairLeft (Black,Node Red a x b,value,right)) - | (True, Black, Node Red Leaf x Leaf, value, right) - => (False,Node Black (Node Red Leaf x Leaf) value right) - | (True,Black, Node Red a x (Node Black b y c),value,right) - => (False, Node Black a x (repairRight (Black,b,y,Node Red c value right))) - | (bf,color,left,value,right) => (bf,Node color left value right) (*Impossible*) +let partionLt compare tree key = + let (_,left,right) = split (fn (key2,_) => + match compare key key2 with + | Less => Less + | _ => Greater + end) tree in (left, right) + +let partionGt compare tree key = + let (_,left,right) = split (fn (key2,_) => + match compare key key2 with + | Greater => Greater + | _ => Less + end) tree in (left, right) + +let rec least tree = + match tree with + | Leaf => None + | Node _ _ Leaf res _ => Some res + | Node _ _ left _ _ => least left end -let rec delMax tree = - match tree with - | Node color left value Leaf => (Some value, checkDeleteRight color left) - | Node color left value right - => let (min,(bf,newright)) = delMax right - in (min,repairAfterDeleteRight(bf,color,left,value,newright)) - | Leaf => (None,(False,Leaf)) +let rec greatest tree = + match tree with + | Leaf => None + | Node _ _ _ res Leaf => Some res + | Node _ _ _ res right => greatest right end -let deleteMax tree = - let (min,(_,newtree)) = delMax tree - in (min,newtree) - -method deleteMax {X, self : Tree X} = deleteMax self - -let rec del elem tree lt = +let rec leastGt compare tree key = match tree with - | Leaf => (False,Leaf) - | Node color left value right - => if lt elem value - then (let (done,newleft) = del elem left lt - in repairAfterDeleteLeft (done,color,newleft,value,right)) - else if lt value elem - then (let (done,newright) = del elem right lt - in repairAfterDeleteRight (done,color,left,value,right)) - else if isEmpty left then checkDeleteLeft color right - else if isEmpty right then checkDeleteRight color left - else (let (maks, (bf,newtree)) = delMax left in - match maks with - | Some v => repairAfterDeleteLeft (bf,color,newtree,v,right) - | None => repairAfterDeleteLeft(bf,color,newtree,elem,right) (*Impossible*) - end) - end - -let delete elem tree lt = let (_,solution) = del elem tree lt in solution - -method remove {X, self : Tree X} elem lt = delete elem self lt - -let insert tree elem lt = - let rec ins tree = - match tree with - | Leaf => Node Red Leaf elem Leaf - | Node color a y b => - if lt elem y then balance (Node color (ins a) y b) - else if lt y elem then balance (Node color a y (ins b)) - else Node color a y b + | Leaf => None + | Node _ _ left (key1, value) right => + match compare key key1 with + | Less => match leastGt compare left key with + | None => Some (key1, value) + | x => x + end + | Equal => least right + | Greater => leastGt compare right key end - let y = ins tree - in match y with - | Node _ y a b => Node Black y a b - | Leaf => Leaf end -method add {X, self : Tree X} elem lt = insert self elem lt - -let toList tree = - let rec _toList tree acc = - match tree with - | Leaf => acc - | Node _ a y b => _toList a (y :: _toList b acc) - end - in _toList tree [] - -method toList {X , self : Tree X} = toList self - -let fromList {X} (lista : List X) lt = - let rec _fromList lista (acc : Tree X) = - match lista with - | x :: xs => _fromList xs (acc.add x lt) - | [] => acc - end - in _fromList lista Leaf - -let rec foldlRB fun acc from = - match from with - | Leaf => acc - | Node _ a y b => - let left = foldlRB fun acc a in - let middle = (fun y left) in - foldlRB fun middle b -end - -let rec foldrRB fun acc from = -match from with - | Leaf => acc - | Node _ a y b => - let right = foldlRB fun acc b in - let middle = (fun y right) in - foldlRB fun middle a -end - -method traversL {X, self : Tree X} fun acc = foldlRB fun acc self -method traversR {X, self : Tree X} fun acc = foldrRB fun acc self - -//TODO: better merge -let merge {X} (from : Tree X) (to : Tree X) lt = - foldlRB (fn x (y : Tree X) => y.add x lt) to from - -let rec member elem tree lt = +let rec leastGeq compare tree key = match tree with - | Leaf => False - | Node _ l v r => - if lt elem v then member elem l lt - else if lt v elem then member elem r lt - else True + | Leaf => None + | Node _ _ left (key1, value) right => + match compare key key1 with + | Less => match leastGeq compare left key with + | None => Some (key1,value) + | x => x + end + | Equal => Some (key1, value) + | Greater => leastGeq compare right key + end end - -method member {X, self : Tree X} elem lt = member elem self lt - - -let add lt tree key value = insert tree (key,value) lt -let join lt tree1 tree2 = merge tree1 tree2 lt -let rmVal lt tree key = match tree with - | Leaf => Leaf - | Node _ _ (_,v) _ => delete (key,v) tree lt -end - -let rec _find lt elem tree = - match tree with +let rec greatestLt compare tree key = + match tree with | Leaf => None - | Node _ l v r => if lt elem v then _find lt elem l - else if lt v elem then _find lt elem r else Some v -end - -//method find {X,self : Tree X} elem lt = _find lt elem self + | Node _ _ left (key1,value) right => + match compare key key1 with + | Less => greatestLt compare left key + | Equal => greatest left + | Greater => match greatestLt compare right key with + | None => Some (key1,value) + | x => x + end + end + end -let find lt tree key = +let rec greatestLeq compare tree key = match tree with - | Leaf => None - | Node _ l v r => let (_,a) = v in _find lt (key,a) tree -end - -let update lt tree key val = let x = rmVal lt tree key in -add lt x key val - -let fst (a,b) = a -let snd (a,b) = b - -pub data OrderedMap Key Val = Map of -{ - T - , empty : T - , method add : T -> Key -> Val -> [] T - , method join : T -> T -> [] T - , method isEmpty : T -> [] Bool - , method deleteElem : T -> Key -> [] T - , method toList : T -> [] List (Pair Key Val) - , method update : T -> Key -> Val -> [] T - , method deleteMax : T -> [] T - , method deleteMin : T -> [] T - , method find : T -> Key -> [] Option (Pair Key Val) -} - -pub data OrderedSet Value = Set of { - T - , empty : T - , method isEmpty : T -> [] Bool - , method insert : T -> Value -> [] T - , method singleton : Value -> [] T - , method remove : T -> Value ->[] T - , method union : T -> T -> [] T - , method find : T -> Value -> [] Bool - , method deleteMax : T -> [] T - , method deleteMin : T -> [] T -} - - -pub let makeMap {Key, Val} (lt : Key -> [] Key -> [] Bool)= -Map { - T = Tree (Pair Key Val) - , empty = Leaf - , method add = add (fn (a,b) (c,d) => lt a c) - , method join = join (fn (a,b) (c,d) => lt a c) - , method isEmpty = isEmpty - , method deleteElem = rmVal (fn (a,b) (c,d) => lt a c) - , method toList = toList - , method update = update (fn (a,_) (key,_) => lt a key) - , method deleteMax = fn mapa => snd (deleteMax mapa) - , method deleteMin = fn mapa => snd (deleteMin mapa) - , method find = find (fn (a,b) (c,d) => lt a c) -} - + | Leaf => None + | Node _ _ left (key1,value) right => + match compare key key1 with + | Less => greatestLt compare left key + | Equal => Some (key1,value) + | Greater => match greatestLeq compare right key with + | None => Some (key1,value) + | x => x + end + end + end -pub let makeSet {Value} (lt : Value -> [] Value -> [] Bool) = -Set { - T = Tree Value +pub let makeOrderedMap {Key} (compare : Key -> Key -> [] Ordered) = Map { + T = Pair Key , empty = Leaf - , method isEmpty = isEmpty - , method insert = fn tree elem => insert tree elem lt - , method singleton = fn elem => insert Leaf elem lt - , method remove = fn tree elem => delete elem tree lt - , method union = join lt - , method find = fn tree elem => member elem tree lt - , method deleteMax = fn mapa => snd (deleteMax mapa) - , method deleteMin = fn mapa => snd (deleteMin mapa) + , singleton = fn key val => Node Black 1 Leaf (key,val) Leaf + , method isEmpty = fn tree => match tree with | Leaf => True | _ => False end + , method insert = fn tree key val => + match search (fn (key', _ ) => compare key key') tree [] with + | (Leaf, zipper) => zipRed (key,val) Leaf Leaf zipper + | ((Node color bulk left _ right), zipper) => + zip (Node color bulk left (key,val) right) zipper + end + , method insert' = fn tree key val => + match search (fn (key', _ ) => compare key key') tree [] with + | (Leaf, zipper) => (zipRed (key,val) Leaf Leaf zipper, False) + | ((Node color bulk left _ right), zipper) => + (zip (Node color bulk left (key,val) right) zipper, True) + end + , method remove = fn tree key => + match search (fn (key', _ ) => compare key key') tree [] with + | (Leaf,_) => tree + | (Node color _ left _ right, zipper) => + delete color left right zipper + end + , method remove' = fn tree key => + match search (fn (key', _ ) => compare key key') tree [] with + | (Leaf,_) => (tree,False) + | (Node color _ left _ right, zipper) => + (delete color left right zipper, True) + end + , method member = member compare + , method find = find compare + , method operate = operate compare + , method foldl = fn tree func acc => foldl func tree acc + , method foldr = fn tree func acc => foldr func tree acc + , method toList = fn tree => + foldr (fn key value acc => (key, value) :: acc) tree [] + , method toValueList = fn tree => + foldr (fn key value acc => value :: acc) tree [] + , method domain = fn tree => + foldr (fn key value acc => key :: acc) tree [] + , method map = fn tree func => map tree func + , method map2 = map2 + , method app = app + , method union = union compare + , method partion = fn tree key => + let (output,left,right) = split (fn (key2,_) => compare key key2) tree + in match output with + | None => (left,None,right) + | Some (_,x) => (left,Some x, right) + end + , method partionLt = partionLt compare + , method partionGt = partionGt compare + , method rangeee = fn tree left right => + let (_,middle) = partionLt compare tree left in + let (result,_) = partionGt compare middle right in result + , method rangeei = fn tree left right => + let (_,middle) = partionLt compare tree left in + let (result,_) = partionLt compare middle right in result + , method rangeie = fn tree left right => + let (_,middle) = partionGt compare tree left in + let (result,_) = partionGt compare middle right in result + , method rangeii = fn tree left right => + let (_,middle) = partionGt compare tree left in + let (result,_) = partionLt compare middle right in result + , method least = least + , method greatest = greatest + , method leastGt = leastGt compare + , method leastGeq = leastGeq compare + , method greatestLt = greatestLt compare + , method greatestLeq = greatestLeq compare } diff --git a/lib/Queue.fram b/lib/Queue.fram index d90a35dd..acc43eb5 100644 --- a/lib/Queue.fram +++ b/lib/Queue.fram @@ -1,5 +1,8 @@ +(* This file is part of DBL, released under MIT license. + * See LICENSE for details. +*) -data MyInt = Zero | Positive of Int +data NotNegativeInt = Zero | Positive of Int let addOne value = match value with @@ -15,17 +18,18 @@ end data RotationState Val = | Idle - | Reversing of MyInt, List Val, List Val, List Val, List Val - | Appending of MyInt, List Val, List Val + | Reversing of NotNegativeInt, List Val, List Val, List Val, List Val + | Appending of NotNegativeInt, List Val, List Val | Done of List Val data HoodMelvilleQueue Val = - | HMQueue of MyInt, List Val, RotationState Val, MyInt, List Val + | HMQueue of NotNegativeInt, List Val, RotationState Val, + NotNegativeInt, List Val let exec state = match state with - | Reversing ok (x::f) f' (y::r) r' - => Reversing (addOne ok) f (x::f') r (y::r') + | Reversing ok (x::f) f' (y::r) r' => + Reversing (addOne ok) f (x::f') r (y::r') | Reversing ok [] f' [y] r' => Appending ok f' (y::r') | Appending Zero f' r' => Done r' | Appending ok (x::f') r' => Appending (subOne ok) f' (x::r') @@ -42,8 +46,8 @@ end let exec_twice hmqueue = match hmqueue with -| HMQueue lenf f state lenr r -=> match exec (exec state) with +| HMQueue lenf f state lenr r => + match exec (exec state) with | Done newf => HMQueue lenf newf Idle lenr r | newstate => HMQueue lenf f newstate lenr r end @@ -66,16 +70,16 @@ end let check queue = match queue with -| HMQueue lenf f state lenr r -=> if leq lenr lenf then exec_twice queue +| HMQueue lenf f state lenr r => +if leq lenr lenf then exec_twice queue else ( let newstate = Reversing Zero f [] r [] in exec_twice (HMQueue (add lenf lenr) f newstate Zero []) ) end -let empty = HMQueue Zero [] Idle Zero [] -let isEmpty queue = +pub let emptyQueue = HMQueue Zero [] Idle Zero [] +pub let isEmpty queue = match queue with | HMQueue Zero _ _ _ _ => True | _ => False @@ -96,30 +100,16 @@ end let tail queue = match queue with -| HMQueue Zero _ _ _ _ => empty -| HMQueue _ [] _ _ _ => empty +| HMQueue Zero _ _ _ _ => emptyQueue +| HMQueue _ [] _ _ _ => emptyQueue | HMQueue lenf (x::xs) state lenr r => check (HMQueue (subOne lenf) xs (invalidate state) lenr r) end -pub data Queue Val = Queue of { - T - , empty : T - , method isEmpty : T -> [] Bool - , method snoc : T -> Val -> [] T - , method tail : T -> [] T - , method push : T -> Val -> [] T - , method pop : T -> [] T - , method head : T -> [] Option Val -} - -pub let makeQueue {Val} = Queue { - T = HoodMelvilleQueue Val - , empty = empty - , method isEmpty = isEmpty - , method snoc = snoc - , method tail = tail - , method push = snoc - , method pop = tail - , method head = head -} \ No newline at end of file + +pub method isEmpty = isEmpty self +pub method snoc = snoc self +pub method tail = tail self +pub method push = snoc self +pub method pop = tail self +pub method head = head self diff --git a/test/stdlib/stdlib0001_SetMap.fram b/test/stdlib/stdlib0001_SetMap.fram deleted file mode 100644 index 232cc070..00000000 --- a/test/stdlib/stdlib0001_SetMap.fram +++ /dev/null @@ -1,19 +0,0 @@ -import OrderedMap - -let lt (v1 : Int) (v2 : Int) = v1 < v2 - -let OrderedMap.Map {module StringMap} = OrderedMap.makeMap lt - -let x = StringMap.empty -let y = x.add 1 "Test 1" -let z = (y.isEmpty == False) && (x.isEmpty == True) -let g = y.deleteElem 1 - -let OrderedMap.Set {module IntSet} = OrderedMap.makeSet lt - -let x = IntSet.empty -let y = x.insert 1 -let z = y.insert 2 -let w = y.deleteMax -let g = w.isEmpty -let f = 5.singleton diff --git a/test/stdlib/stdlib0002_Queue.fram b/test/stdlib/stdlib0002_Queue.fram deleted file mode 100644 index 8428178f..00000000 --- a/test/stdlib/stdlib0002_Queue.fram +++ /dev/null @@ -1,11 +0,0 @@ -import Queue - -let Queue.Queue {module IntQ} = Queue.makeQueue - -let x = IntQ.empty -let _ = if x.isEmpty then 1 else 0 -let y = x.push 1 -let w = y.head -let _ = if y.isEmpty then 1 else 0 -let z = y.pop -let _ = if z.isEmpty then 1 else 0 From e5d206fca5b28f722f83b759699cb0c8b9836bcd Mon Sep 17 00:00:00 2001 From: Jakub Chomiczewski Date: Wed, 14 Aug 2024 09:23:11 +0200 Subject: [PATCH 07/27] Adding missing files --- lib/Comparable.fram | 5 + lib/Ordered.fram | 14 ++ lib/OrderedMapSignature.fram | 63 +++++++ lib/OrderedSet.fram | 232 +++++++++++++++++++++++++ lib/OrderedSetSignature.fram | 34 ++++ lib/RedBlackTree.fram | 278 ++++++++++++++++++++++++++++++ test/stdlib/stdlib0001_Map.fram | 92 ++++++++++ test/stdlib/stdlib0002_Set.fram | 75 ++++++++ test/stdlib/stdlib0003_Queue.fram | 20 +++ 9 files changed, 813 insertions(+) create mode 100644 lib/Comparable.fram create mode 100644 lib/Ordered.fram create mode 100644 lib/OrderedMapSignature.fram create mode 100644 lib/OrderedSet.fram create mode 100644 lib/OrderedSetSignature.fram create mode 100644 lib/RedBlackTree.fram create mode 100644 test/stdlib/stdlib0001_Map.fram create mode 100644 test/stdlib/stdlib0002_Set.fram create mode 100644 test/stdlib/stdlib0003_Queue.fram diff --git a/lib/Comparable.fram b/lib/Comparable.fram new file mode 100644 index 00000000..9bf47049 --- /dev/null +++ b/lib/Comparable.fram @@ -0,0 +1,5 @@ +(* This file is part of DBL, released under MIT license. + * See LICENSE for details. +*) + +pub data Comparable = Eq| Noteq diff --git a/lib/Ordered.fram b/lib/Ordered.fram new file mode 100644 index 00000000..e72f9455 --- /dev/null +++ b/lib/Ordered.fram @@ -0,0 +1,14 @@ +(* This file is part of DBL, released under MIT license. + * See LICENSE for details. +*) + +import open Comparable + +pub data Ordered = +| Less +| Equal +| Greater + +pub let ordToComp elem = match elem with | Equal => Eq | _ => Noteq end + +pub method toComparable {self : Ordered} = ordToComp self diff --git a/lib/OrderedMapSignature.fram b/lib/OrderedMapSignature.fram new file mode 100644 index 00000000..a307fb01 --- /dev/null +++ b/lib/OrderedMapSignature.fram @@ -0,0 +1,63 @@ +(* This file is part of DBL, released under MIT license. + * See LICENSE for details. +*) +import open RedBlackTree + +pub data OrderedMap Key = Map of { + T + , empty : {type Val} -> Tree (T Val) + , singleton : {type Val} -> Key -> Val -> [] Tree (T Val) + , method isEmpty : {type Val} -> Tree (T Val) -> [] Bool + , method insert : {type Val} -> Tree (T Val) -> + Key -> Val -> [] Tree (T Val) + , method insert' : {type Val} -> Tree (T Val) -> + Key -> Val -> [] (Pair (Tree (T Val)) Bool) + , method remove : {type Val} -> Tree (T Val) -> + Key -> [] Tree (T Val) + , method remove' : {type Val} -> Tree (T Val) -> + Key -> [] (Pair (Tree (T Val)) Bool) + , method member : {type Val} -> Tree (T Val) -> Key -> [] Bool + , method find : {type Val} -> Tree (T Val) -> Key -> [] Option Val + , method operate : {type Val} -> Tree (T Val) -> Key -> + (Unit -> [] Option Val) -> (Val -> [] Option Val) -> + [] (Pair (Pair (Option Val) (Option Val)) (Tree (T Val))) + , method foldl : {type Val, type A} -> Tree (T Val) -> + (Key -> Val -> A -> [] A) -> A -> [] A + , method foldr : {type Val, type A} -> Tree (T Val) -> + (Key -> Val -> A -> [] A) -> A -> [] A + , method toList : {type Val} -> Tree (T Val) -> [] List (Pair Key Val) + , method toValueList : {type Val} -> Tree (T Val) -> [] List Val + , method domain : {type Val} -> Tree (T Val) -> [] List Key + , method map : {type Val, type A} -> Tree (T Val) -> + (Val -> [] A) -> [] Tree (T A) + , method map2 : {type Val, type A} -> Tree (T Val) -> + (Key -> [] A) -> [] Tree (T A) +(* , method map3 : {type Val, type A} -> (Val -> [] A) -> + Tree (T Val) -> [] Tree (T A) *) + , method app : {type Val} -> Tree (T Val) -> + (Key -> Val -> [] Unit) -> [] Unit + , method union : {type Val} -> Tree (T Val) -> Tree (T Val) -> + (Key -> Val -> Val -> [] Val) -> [] Tree (T Val) + , method partion : {type Val} -> Tree (T Val) -> Key -> + [] (Pair (Pair (Tree (T Val)) (Option Val)) (Tree (T Val))) + , method partionLt : {type Val} -> Tree (T Val) -> Key -> + [] Pair (Tree (T Val)) (Tree (T Val)) + , method partionGt : {type Val} -> Tree (T Val) -> Key -> + [] Pair (Tree (T Val)) (Tree (T Val)) + , method rangeii : {type Val} -> Tree (T Val) -> Key -> Key -> + [] Tree (T Val) + , method rangeie : {type Val} -> Tree (T Val) -> Key -> Key -> + [] Tree (T Val) + , method rangeei : {type Val} -> Tree (T Val) -> Key -> Key -> + [] Tree (T Val) + , method rangeee : {type Val} -> Tree (T Val) -> Key -> Key -> + [] Tree (T Val) + , method least : {type Val} -> Tree (T Val) -> [] Option (T Val) + , method greatest : {type Val} -> Tree (T Val) -> [] Option (T Val) + , method leastGt : {type Val} -> Tree (T Val) -> Key -> [] Option (T Val) + , method leastGeq : {type Val} -> Tree (T Val) -> Key -> [] Option (T Val) + , method greatestLt : {type Val} -> Tree (T Val) -> + Key -> [] Option (T Val) + , method greatestLeq : {type Val} -> Tree (T Val) -> + Key -> [] Option (T Val) +} diff --git a/lib/OrderedSet.fram b/lib/OrderedSet.fram new file mode 100644 index 00000000..1b854424 --- /dev/null +++ b/lib/OrderedSet.fram @@ -0,0 +1,232 @@ +(* This file is part of DBL, released under MIT license. + * See LICENSE for details. +*) + +import open RedBlackTree +import open OrderedSetSignature + +data rec Q Val = Nil | E of Val , Q Val | T of Tree Val , Q Val + +let rec eqMain eq qs1 qs2 = + match (qs1,qs2) with + | (Nil,Nil) => True + | (Nil, E _ _) => False + | (E _ _, Nil) => False + | (T Leaf rest, _) => eqMain eq rest qs2 + | (_, T Leaf rest) => eqMain eq qs1 rest + | (T (Node _ _ left elem right) rest, _) => + eqMain eq (T left (E elem (T right rest))) qs2 + | (_, T (Node _ _ left elem right) rest) => + eqMain eq qs1 (T left (E elem (T right rest))) + | (E elem1 rest1, E elem2 rest2) => + match eq elem1 elem2 with + | Noteq => False + | Eq => eqMain eq rest1 rest2 + end + end + +let rec subsetMain comp qs1 qs2 = + match (qs1,qs2) with + | (Nil,_) => True + | (E _ _ , Nil) => False + | (T Leaf rest, _) => subsetMain comp rest qs2 + | (_ , T Leaf rest) => subsetMain comp qs1 rest + | (T (Node _ _ left elem right) rest, _) => + subsetMain comp (T left (E elem (T right rest))) qs2 + | (_, T (Node _ _ left elem right) rest) => + subsetMain comp qs1 (T left (E elem (T right rest))) + | (E elem1 rest1, E elem2 rest2) => + match comp elem1 elem2 with + | Less => False + | Equal => subsetMain comp rest1 rest2 + | Greater => subsetMain comp qs1 rest2 + end + end + +let partionLt compare = fn tree key1 => let (_,left,right) = + split (fn key2 => match compare key1 key2 with + | Greater => Greater | _ => Less end) tree in (left,right) + +let partionGt compare = fn tree key1 => let (_, left,right) = + split (fn key2 => match compare key1 key2 with + | Less => Less | _ => Greater end) tree in (left,right) + +let rec least tree = + match tree with + | Leaf => None + | Node _ _ Leaf x _ => Some x + | Node _ _ left _ _ => least left + end + +let rec greatest tree = + match tree with + | Leaf => None + | Node _ _ _ x Leaf => Some x + | Node _ _ _ _ right => greatest right + end + +pub let makeOrderedSet {Val} (compare : Val -> Val -> [] Ordered) = Set { + T = Tree Val + , empty = Leaf + , method isEmpty = + (fn tree => match tree with + | Leaf => True + | _ => False + end) + , method singletonSet = fn elem => Node Black 1 Leaf elem Leaf + , singleton = fn elem => Node Black 1 Leaf elem Leaf + , method insert = fn tree elem => + match search (fn val => compare elem val) tree [] with + | (Leaf,zipper) => zipRed elem Leaf Leaf zipper + | (Node _ _ _ _ _,_) => tree + end + , method remove = fn tree elem => + match search (fn val => compare elem val) tree [] with + | (Leaf,_) => tree + | (Node color _ left _ right,zipper) => delete color left right zipper + end + , method member = fn tree elem => let rec search tree elem = + match tree with + | Leaf => False + | Node _ _ left val right => + match compare elem val with + | Less => search left elem + | Greater => search right elem + | Equal => True + end + end in search tree elem + , method foldl = fn tree func acc => let rec foldl tree func acc = + match tree with + | Leaf => acc + | Node _ _ left val right => + foldl right func (func val (foldl left func acc)) + end in foldl tree func acc + , method foldr = fn tree func acc => let rec foldr tree func acc = + match tree with + | Leaf => acc + | Node _ _ left val right => + foldr left func (func val (foldr right func acc)) + end in foldr tree func acc + , method toList = fn tree => let rec toList tree acc = + match tree with + | Leaf => acc + | Node _ _ left val right => + toList left (val :: toList right acc) + end in toList tree [] + , method union = fn tree1 tree2 => let rec union tree1 tree2 = + match tree1 with + | Leaf => tree2 + | Node _ _ left1 key1 right1 => + match tree2 with + | Leaf => tree1 + | Node _ _ _ _ _ => + let (_,left2,right2) = split (fn key2 => compare key1 key2) tree2 + in join_val key1 (union left1 left2) (union right1 right2) + end + end in union tree1 tree2 + , method intersection = fn tree1 tree2 => let rec intersection tree1 tree2 = + match tree1 with + | Leaf => Leaf + | Node _ _ left1 key1 right1 => + match tree2 with + | Leaf => Leaf + | _ => let (value_out, left2, right2) = + split (fn key2 => compare key1 key2) tree2 + in let left = intersection left1 left2 + in let right = intersection right1 right2 + in match value_out with + | Some _ => join_val key1 left right + | None => join left right + end + end + end in intersection tree1 tree2 + , method diffrence = fn tree1 tree2 => let rec diffrence tree1 tree2 = + match tree1 with + | Leaf => Leaf + | Node _ _ left1 key1 right1 => + match tree2 with + | Leaf => tree1 + | _ => let (value_out, left2, right2) = + split (fn key2 => compare key1 key2) tree2 + in let left = diffrence left1 left2 + in let right = diffrence right1 right2 + in match value_out with + | Some _ => join left right + | None => join_val key1 left right + end + end + end in diffrence tree1 tree2 + , method eq = fn set1 set2 => + eqMain (fn e1 e2 => (compare e1 e2).toComparable) (T set1 Nil) (T set2 Nil) + , method subset = fn set1 set2 => subsetMain compare (T set1 Nil) (T set2 Nil) + , method partionLt = partionLt compare + , method partionGt = partionGt compare + , method rangeii = fn tree left right => + let (_, tree') = partionLt compare tree left in + let (tree'',_) = partionGt compare tree' right in tree'' + , method rangeei = fn tree left right => + let (_, tree') = partionGt compare tree left in + let (tree'',_) = partionGt compare tree' right in tree'' + , method rangeie = fn tree left right => + let (_, tree') = partionLt compare tree left in + let (tree'',_) = partionLt compare tree' right in tree'' + , method rangeee = fn tree left right => + let (_, tree') = partionGt compare tree left in + let (tree'',_) = partionLt compare tree' right in tree'' + , method least = fn tree => least tree + , method greatest = fn tree => greatest tree + , method leastGt = fn tree val => let rec leastGt tree val = + match tree with + | Leaf => None + | Node _ _ left key right => + match compare val key with + | Less => let x = leastGt left val in + match x with + | None => Some key + | _ => x + end + | Equal => least right + | Greater => leastGt right val + end + end in leastGt tree val + , method leastGeq = fn tree val => let rec leastGeq tree val = + match tree with + | Leaf => None + | Node _ _ left key right => + match compare val key with + | Less => match leastGeq left val with + | None => Some key + | x => x + end + | Equal => Some val + | Greater => leastGeq right val + end + end in leastGeq tree val + , method greatestLt = fn tree val => let rec greatestLt tree val = + match tree with + | Leaf => None + | Node _ _ left key right => + match compare val key with + | Less => greatestLt left val + | Equal => greatest left + | Greater => match greatestLt right val with + | None => Some key + | x => x + end + end + end in greatestLt tree val + , method greatestLeq = fn tree val => + let rec greatestLeq tree val = + match tree with + | Leaf => None + | Node _ _ left key right => + match compare val key with + | Less => greatestLeq left val + | Equal => Some val + | Greater => match greatestLeq right val with + | None => Some key + | x => x + end + end + end in greatestLeq tree val +} diff --git a/lib/OrderedSetSignature.fram b/lib/OrderedSetSignature.fram new file mode 100644 index 00000000..45e9aebd --- /dev/null +++ b/lib/OrderedSetSignature.fram @@ -0,0 +1,34 @@ +(* This file is part of DBL, released under MIT license. + * See LICENSE for details. +*) + +pub data OrderedSet Val = Set of { + T + , empty : T + , method isEmpty : T -> [] Bool + , singleton : Val -> [] T + , method insert : T -> Val -> [] T + , method remove : T -> Val -> [] T + , method singletonSet : Val -> [] T + , method member : T -> Val -> [] Bool + , method foldl : {type A} -> T -> (Val -> A -> [] A) -> A -> [] A + , method foldr : {type A} -> T -> (Val -> A -> [] A) -> A -> [] A + , method toList : T -> [] List Val + , method union : T -> T -> [] T + , method intersection : T -> T -> [] T + , method diffrence : T -> T -> [] T + , method eq : T -> T -> [] Bool + , method subset : T -> T -> [] Bool + , method partionLt : T -> Val -> [] (Pair T T) + , method partionGt : T -> Val -> [] (Pair T T) + , method rangeii : T -> Val -> Val -> [] T + , method rangeei : T -> Val -> Val -> [] T + , method rangeie : T -> Val -> Val -> [] T + , method rangeee : T -> Val -> Val -> [] T + , method least : T -> [] Option Val + , method greatest : T -> [] Option Val + , method leastGt : T -> Val -> [] Option Val + , method leastGeq : T -> Val -> [] Option Val + , method greatestLt : T -> Val -> [] Option Val + , method greatestLeq : T -> Val -> [] Option Val +} diff --git a/lib/RedBlackTree.fram b/lib/RedBlackTree.fram new file mode 100644 index 00000000..a0fd992b --- /dev/null +++ b/lib/RedBlackTree.fram @@ -0,0 +1,278 @@ +(* This file is part of DBL, released under MIT license. + * See LICENSE for details. +*) + +import open Ordered +import List + +pub rec + data Color = + | Red + | Black + data Tree Value = + | Leaf + | Node of Color, Int, Tree Value, Value, Tree Value + data ZipElem Value = + | Left of Color, Value, Tree Value + | Right of Color, Value, Tree Value +end + +pub let empty = Leaf + +pub let size tree = + match tree with + | Leaf => 0 + | Node _ bulk _ _ _ => bulk + end + +pub let makeNode color left value right = + Node color (size left + size right + 1) left value right + +pub let rec zip tree zipper = + match zipper with + | [] => tree + + | Left color value right :: rest => zip (makeNode color tree value right) rest + + | Right color value left :: rest => zip (makeNode color left value tree) rest + + end + +pub let rec zipRed value left right zipper = + match zipper with + | [] => makeNode Black left value right + + | Left Black value1 right1 :: rest => + zip (makeNode Black (makeNode Red left value right) value1 right1) rest + + | Right Black value1 left1 :: rest => + zip (makeNode Black left1 value1 (makeNode Red left value right)) rest + + | Left Red value1 right1 :: + Left _ value2 (Node Red bulk3 left3 value3 right3) :: + rest => zipRed value2 + (makeNode Black (makeNode Red left value right) value1 right1) + (Node Black bulk3 left3 value3 right3) rest + + | Left Red value1 right1 :: + Right _ value2 (Node Red bulk3 left3 value3 right3) :: + rest => zipRed value2 + (Node Black bulk3 left3 value3 right3) + (makeNode Black (makeNode Red left value right) value1 right1) rest + + | Right Red value1 left1 :: + Left _ value2 (Node Red bulk3 left3 value3 right3) :: + rest => zipRed value2 + (makeNode Black left1 value1 (makeNode Red left value right)) + (Node Black bulk3 left3 value3 right3) rest + + | Right Red value1 left1 :: + Right _ value2 (Node Red bulk3 left3 value3 right3) :: + rest => zipRed value2 (Node Black bulk3 left3 value3 right3) + (makeNode Black left1 value1 (makeNode Red left value right)) rest + + | Left Red value1 right1 :: + Left _ value2 node3 :: + rest => zip (makeNode Black (makeNode Red left value right) value1 + (makeNode Red right1 value2 node3)) rest + + | Left Red value1 right1 :: + Right _ value2 node3 :: + rest => zip (makeNode Black (makeNode Red node3 value2 left) + value (makeNode Red right value1 right1)) rest + + | Right Red value1 left1 :: + Left _ value2 node3 :: + rest => zip (makeNode Black (makeNode Red left1 value1 left) + value (makeNode Red right value2 node3)) rest + + | Right Red value1 left1 :: + Right _ value2 node3 :: + rest => zip (makeNode Black (makeNode Red node3 value2 left1) + value1 (makeNode Red left value right)) rest + + | Left Red value1 right1 :: + [] => makeNode Black (makeNode Red left value right) value1 right1 + + | Right Red value1 left1 :: + [] => makeNode Black left1 value1 (makeNode Red left value right) + + end + +pub let rec zipBlack tree zipper = + match zipper with + | [] => tree + + | Left color1 value1 (Node _ _ left2 value2 + (Node Red bulk3 left3 value3 right3)) + :: rest => zip (makeNode color1 (makeNode Black tree value1 left2 ) value2 + (Node Black bulk3 left3 value3 right3)) rest + + | Right color1 value1 (Node _ _ (Node Red bulk3 left3 value3 right3) + value2 right2) :: rest => zip (makeNode color1 + (Node Black bulk3 left3 value3 right3) value2 + (makeNode Black right2 value1 tree)) rest + + | Left color1 value1 (Node _ _ (Node Red _ left3 value3 right3) + value2 right2) :: rest => zip (makeNode color1 + (makeNode Black tree value1 left3) value3 + (makeNode Black right3 value2 right2)) rest + + | Right color1 value1 (Node _ _ left2 value2 (Node Red _ left3 value3 + right3)) :: rest => zip (makeNode color1 (makeNode Black left2 value2 left3) + value3 (makeNode Black right3 value1 tree)) rest + + | Left Red value1 (Node _ bulk2 left2 value2 right2) + :: rest => zip (makeNode Black tree value1 + (Node Red bulk2 left2 value2 right2)) rest + + | Right Red value1 (Node _ bulk2 left2 value2 right2) + :: rest => zip (makeNode Black (Node Red bulk2 left2 value2 right2) + value1 tree) rest + + | Left Black value1 (Node Black bulk2 left2 value2 right2) + :: rest => zipBlack (makeNode Black tree value1 + (Node Red bulk2 left2 value2 right2)) rest + + | Right Black value1 (Node Black bulk2 left2 value2 right2) + :: rest => zipBlack (makeNode Black (Node Red bulk2 left2 value2 + right2) value1 tree) rest + + | Left Black value1 (Node Red _ left2 value2 right2) :: rest + => zipBlack tree (Left Red value1 left2 :: Left Black + value2 right2 :: rest) + + | Right Black value1 (Node Red _ left2 value2 right2) :: rest + => zipBlack tree (Right Red value1 right2 :: Right Black + value2 left2 :: rest) + + | Left _ _ Leaf :: _ => tree + + | Right _ _ Leaf :: _ => tree + + end + +pub let rec search func tree zipper = + match tree with + | Leaf => (Leaf, zipper) + | Node color _ left value right => + match func value with + | Less => search func left (Left color value right :: zipper) + | Greater => search func right (Right color value left :: zipper) + | Equal => (tree, zipper) + end + end + +pub let rec searchMin tree zipper = + match tree with + | Leaf => zipper + | Node color _ left value right => + searchMin left (Left color value right :: zipper) + end + +pub let rec searchMax tree zipper = + match tree with + | Leaf => zipper + | Node color _ left value right => + searchMax right (Right color value left :: zipper) + end + +pub let deleteNearLeaf color child zipper = + match color with + | Red => zip Leaf zipper + | Black => match child with + | Node _ _ _ value _ => zip (makeNode Black Leaf value Leaf) zipper + | Leaf => zipBlack Leaf zipper + end + end + +pub let delete color left right zipper = + match right with + | Leaf => match left with + | Leaf => match color with + | Red => zip Leaf zipper + | Black => zipBlack Leaf zipper + end + | _ => match searchMax left [] with + | Right colorLeftMin valueLeftMin leftLeftMin :: zipperr + => deleteNearLeaf colorLeftMin leftLeftMin + (List.append zipperr (Left color valueLeftMin right :: zipper)) + | _ => Leaf + end + end + | _ => match searchMin right [] with + | Left colorRightMin valueRightMin rightRightMin :: zipperr + => deleteNearLeaf colorRightMin rightRightMin + (List.append zipperr (Right color valueRightMin left :: zipper)) + | _ => Leaf + end + end + +pub let blacken tree = + match tree with + | Node Red bulk left value right => Node Black bulk left value right + | _ => tree + end + +pub let rec blackHeight tree acc = + match tree with + | Leaf => acc + | Node Red _ left _ _ => blackHeight left acc + | Node Black _ left _ _ => blackHeight left (1 + acc) + end + +pub let rec searchHeight leftward target tree zipper = + match tree with + | Leaf => (Leaf, zipper) + | Node Red _ left value right => + if leftward then + searchHeight leftward target left (Left Red value right :: zipper) + else + searchHeight leftward target right (Right Red value left :: zipper) + | Node Black _ left value right => + if 0 == target then + (tree,zipper) + else if leftward then + searchHeight leftward (target - 1) left (Left Black value right :: zipper) + else + searchHeight leftward (target - 1) right (Right Black value left :: zipper) + end + +pub let join_val value left right = + let left = blacken left in + let right = blacken right in + let lbh = blackHeight left 0 in + let rbh = blackHeight right 0 in + if lbh == rbh then + makeNode Black left value right + else if lbh > rbh then + (let (_left, zipper) = searchHeight False (lbh-rbh) left [] in + zipRed value _left right zipper) + else + (let (_right, zipper) = searchHeight True (rbh-lbh) right [] in + zipRed value left _right zipper) + +pub let join left right = + match left with + | Leaf => right + | _ => match right with + | Leaf => left + | _ => match searchMax left [] with + | Right color value leftSmall :: zipper + => join_val value (deleteNearLeaf color leftSmall zipper) right + |_ => left + end + end + end + +pub let rec split func tree = + match tree with + | Leaf => (None,Leaf,Leaf) + | Node _ _ left value right => match func value with + | Equal => (Some value, left, right) + | Less => let (_v, _l, _r) = split func left in + (_v, _l, join_val value _r right) + | Greater => let (_v, _l, _r) = split func right in + (_v, join_val value left _l, _r) + end + end diff --git a/test/stdlib/stdlib0001_Map.fram b/test/stdlib/stdlib0001_Map.fram new file mode 100644 index 00000000..af01ffac --- /dev/null +++ b/test/stdlib/stdlib0001_Map.fram @@ -0,0 +1,92 @@ +import OrderedMap +import open List +import open Ordered +import open Prelude + +let assert condition = +if condition then () else exit 1 + +let lt (v1 : Int) (v2 : Int) = + if v1 < v2 then Less + else if v2 < v1 then Greater + else Equal + +let OrderedMap.Map {module IntMap} = OrderedMap.makeOrderedMap lt + +let x = IntMap.empty + +(* insert check *) +let y = x.insert 1 1 +let z = x.insert 1 "a" + +(* isEmpty check *) +let _ = assert (y.isEmpty == False) +let _ = assert (z.isEmpty == False) +let _ = assert (y.remove 1 >. isEmpty) + +(* singleton check *) +let y = IntMap.singleton 1 1 +let _ = assert (y.toValueList == [1]) + +(* domain check *) +let z = y.insert 2 1 >. insert 3 2 >. insert 4 3 +let _ = assert (z.domain == [1,2,3,4] && z.toValueList == [1,1,2,3]) + +(* toList check *) +let _ = assert ((z.toList.foldLeft + (fn acc (key,val) => val :: acc) []) == [1,1,2,3].rev) + +(* foldl check *) +let _ = assert (z.foldl (fn key val acc => key :: acc) [] == [1,2,3,4].rev) + +(* member check *) +let _ = assert (z.member 1) + +(* find check *) +let _ = assert (match z.find 1 with | None => False | _ => True end) + +(* operate change check *) +let _ = assert (snd (z.operate 1 (fn () => Some 2) (fn a => Some 0)) + >. toValueList == [0,1,2,3]) + +(* operate add check *) +let _ = assert (snd (z.operate 0 (fn () => Some 2) (fn a => Some 0)) + >. toValueList == [2,1,1,2,3]) + +(* map check *) +let _ = assert (z.map (fn x => if x == x.shiftr 1 >. shiftl 1 then -x else x) + >. toValueList == [1,1,(0-2),3]) + +(* union check *) +let y = x.insert 1.neg 2 >. insert 2.neg 3 >. insert 0 1 >. insert 1 10 +let w = z.union y (fn key val1 val2 => val2) +let _ = assert (w.toValueList == [3,2,1,10,1,2,3]) + +(* partion check *) +let q = w.partion 0 +let _ = assert (fst (fst q) >. toValueList == [3,2]) +let _ = assert (snd q >. toValueList == [10,1,2,3]) + +(* partionLt check *) +let q = w.partionLt 0 +let _ = assert (fst q >. toValueList == [3,2,1]) +let _ = assert (snd q >. toValueList == [10,1,2,3]) + +(* partionGt check *) +let q = w.partionGt 0 +let _ = assert (fst q >. toValueList == [3,2]) +let _ = assert (snd q >. toValueList == [1,10,1,2,3]) + +(* rangeee check *) +let q = w.rangeee 0 2 +let _ = assert (q.toValueList == [10]) + +(* rangeii check *) +let q = w.rangeii 0 2 +let _ = assert (q.toValueList == [1,10,1]) + +(* rangeie check *) +let _ = assert (w.rangeie 0 2 >. toValueList == [1,10]) + +(* rangeei check *) +let _ = assert (w.rangeei 0 2 >. toValueList == [10,1]) diff --git a/test/stdlib/stdlib0002_Set.fram b/test/stdlib/stdlib0002_Set.fram new file mode 100644 index 00000000..0ad5cc5a --- /dev/null +++ b/test/stdlib/stdlib0002_Set.fram @@ -0,0 +1,75 @@ +import OrderedSet +import open List +import open Ordered +import open Prelude + +let assert condition = +if condition then () else exit 1 + +let lt (v1 : Int) (v2 : Int) = + if v1 < v2 then Less + else if v2 < v1 then Greater + else Equal + +let OrderedSet.Set {module IntSet} = OrderedSet.makeOrderedSet lt + +(* empty check *) +let x = IntSet.empty +let _ = assert (x.isEmpty) + +(* singletonSet check *) +let x = 0.singletonSet +let _ = assert (not x.isEmpty) + +(* toList check *) +let _ = assert (x.toList == [0]) + +(* insert check *) +let y = x.insert 1 +let _ = assert (y.toList == [0,1]) +let _ = assert (y.insert 2 >. toList == [0,1,2]) + +(* remove check *) +let y = y.insert 2 >. insert 3 +let _ = assert (y.remove 1 >. toList == [0,2,3]) + +(* member check *) +let _ = assert (y.member 1) +let _ = assert (not (y.member 10)) + +(* foldl/r check *) +let _ = assert (y.foldl (fn x acc => x + acc) 0 == 6) +let _ = assert (y.foldr (fn x acc => x + acc) 0 == 6) + +(* union check *) +let x = x.insert 4 >. insert 5 >. insert 6 +let _ = (y.union x >. toList == [0,1,2,3,4,5,6]) + +(* intersection check *) +let _ = assert (x.intersection y >. toList == [0]) + +(* diffrence check *) +let _ = assert (y.diffrence x >. toList == [1,2,3]) +let _ = assert (x.diffrence y >. toList == [4,5,6]) + +(* eq check *) +let _ = assert (x.eq x) +let _ = assert (not (x.eq y)) + +(* subset check *) +let _ = assert (IntSet.empty.subset x) +let _ = assert (IntSet.empty.insert 0 >. insert 1 >. subset y) +let _ = assert (not (x.subset y)) + +(* partionLt check *) +let _ = assert (fst (y.partionLt 2) >. toList == [0,1]) +let _ = assert (snd (y.partionLt 2) >. toList == [2,3]) + +(* rangeii check *) +let _ = assert (y.rangeii 1 2 >. toList == [1,2]) + +(* least check *) +let _ = assert (match y.least with | Some x => x == 0 | _ => False end) + +(* greatest check *) +let _ = assert (match y.greatest with | Some x => x == 3 | _ => False end) \ No newline at end of file diff --git a/test/stdlib/stdlib0003_Queue.fram b/test/stdlib/stdlib0003_Queue.fram new file mode 100644 index 00000000..fbab08df --- /dev/null +++ b/test/stdlib/stdlib0003_Queue.fram @@ -0,0 +1,20 @@ +import Queue + + +let assert condition = +if condition then () else exit 1 + +let compare (x : Int) (y : Int) = x == y +let get_val x = +match x with +| Some x => x +| _ => -1 +end + +let x = Queue.emptyQueue +let x = x.push 1 +let _ = assert (x.isEmpty == False && compare (get_val x.head) 1) +let x = x.pop +let _ = assert x.isEmpty +let x = x >. push 1 >. push 2 >. push 3 +let _ = assert (x.isEmpty == False && compare (get_val x.head) 1 && compare (get_val (x.pop >. head)) 2 && compare (get_val (x.pop >. pop >. head)) 3) From 5b3cd887e7089066d24c17b2e0295aa78166c408 Mon Sep 17 00:00:00 2001 From: Jakub Chomiczewski <49335730+MinionJakub@users.noreply.github.com> Date: Thu, 15 Aug 2024 10:49:12 +0200 Subject: [PATCH 08/27] Correcting a test file --- test/stdlib/stdlib0003_Queue.fram | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/test/stdlib/stdlib0003_Queue.fram b/test/stdlib/stdlib0003_Queue.fram index fbab08df..49d8ef04 100644 --- a/test/stdlib/stdlib0003_Queue.fram +++ b/test/stdlib/stdlib0003_Queue.fram @@ -1,6 +1,5 @@ import Queue - let assert condition = if condition then () else exit 1 @@ -17,4 +16,6 @@ let _ = assert (x.isEmpty == False && compare (get_val x.head) 1) let x = x.pop let _ = assert x.isEmpty let x = x >. push 1 >. push 2 >. push 3 -let _ = assert (x.isEmpty == False && compare (get_val x.head) 1 && compare (get_val (x.pop >. head)) 2 && compare (get_val (x.pop >. pop >. head)) 3) +let _ = assert (x.isEmpty == False && compare (get_val x.head) 1 && + compare (get_val (x.pop >. head)) 2 && + compare (get_val (x.pop >. pop >. head)) 3) From eb36254b2655dd53463dfd8e74b6a0d39d6bd680 Mon Sep 17 00:00:00 2001 From: Jakub Chomiczewski Date: Tue, 29 Oct 2024 14:50:12 +0100 Subject: [PATCH 09/27] Correcting definitions --- lib/OrderedMapSignature.fram | 106 +++++++++++++++++------------------ lib/OrderedSetSignature.fram | 50 ++++++++--------- 2 files changed, 78 insertions(+), 78 deletions(-) diff --git a/lib/OrderedMapSignature.fram b/lib/OrderedMapSignature.fram index a307fb01..058ab79a 100644 --- a/lib/OrderedMapSignature.fram +++ b/lib/OrderedMapSignature.fram @@ -7,57 +7,57 @@ pub data OrderedMap Key = Map of { T , empty : {type Val} -> Tree (T Val) , singleton : {type Val} -> Key -> Val -> [] Tree (T Val) - , method isEmpty : {type Val} -> Tree (T Val) -> [] Bool - , method insert : {type Val} -> Tree (T Val) -> - Key -> Val -> [] Tree (T Val) - , method insert' : {type Val} -> Tree (T Val) -> - Key -> Val -> [] (Pair (Tree (T Val)) Bool) - , method remove : {type Val} -> Tree (T Val) -> - Key -> [] Tree (T Val) - , method remove' : {type Val} -> Tree (T Val) -> - Key -> [] (Pair (Tree (T Val)) Bool) - , method member : {type Val} -> Tree (T Val) -> Key -> [] Bool - , method find : {type Val} -> Tree (T Val) -> Key -> [] Option Val - , method operate : {type Val} -> Tree (T Val) -> Key -> - (Unit -> [] Option Val) -> (Val -> [] Option Val) -> - [] (Pair (Pair (Option Val) (Option Val)) (Tree (T Val))) - , method foldl : {type Val, type A} -> Tree (T Val) -> - (Key -> Val -> A -> [] A) -> A -> [] A - , method foldr : {type Val, type A} -> Tree (T Val) -> - (Key -> Val -> A -> [] A) -> A -> [] A - , method toList : {type Val} -> Tree (T Val) -> [] List (Pair Key Val) - , method toValueList : {type Val} -> Tree (T Val) -> [] List Val - , method domain : {type Val} -> Tree (T Val) -> [] List Key - , method map : {type Val, type A} -> Tree (T Val) -> - (Val -> [] A) -> [] Tree (T A) - , method map2 : {type Val, type A} -> Tree (T Val) -> - (Key -> [] A) -> [] Tree (T A) -(* , method map3 : {type Val, type A} -> (Val -> [] A) -> - Tree (T Val) -> [] Tree (T A) *) - , method app : {type Val} -> Tree (T Val) -> - (Key -> Val -> [] Unit) -> [] Unit - , method union : {type Val} -> Tree (T Val) -> Tree (T Val) -> - (Key -> Val -> Val -> [] Val) -> [] Tree (T Val) - , method partion : {type Val} -> Tree (T Val) -> Key -> - [] (Pair (Pair (Tree (T Val)) (Option Val)) (Tree (T Val))) - , method partionLt : {type Val} -> Tree (T Val) -> Key -> - [] Pair (Tree (T Val)) (Tree (T Val)) - , method partionGt : {type Val} -> Tree (T Val) -> Key -> - [] Pair (Tree (T Val)) (Tree (T Val)) - , method rangeii : {type Val} -> Tree (T Val) -> Key -> Key -> - [] Tree (T Val) - , method rangeie : {type Val} -> Tree (T Val) -> Key -> Key -> - [] Tree (T Val) - , method rangeei : {type Val} -> Tree (T Val) -> Key -> Key -> - [] Tree (T Val) - , method rangeee : {type Val} -> Tree (T Val) -> Key -> Key -> - [] Tree (T Val) - , method least : {type Val} -> Tree (T Val) -> [] Option (T Val) - , method greatest : {type Val} -> Tree (T Val) -> [] Option (T Val) - , method leastGt : {type Val} -> Tree (T Val) -> Key -> [] Option (T Val) - , method leastGeq : {type Val} -> Tree (T Val) -> Key -> [] Option (T Val) - , method greatestLt : {type Val} -> Tree (T Val) -> - Key -> [] Option (T Val) - , method greatestLeq : {type Val} -> Tree (T Val) -> - Key -> [] Option (T Val) + , method isEmpty : {type Val,E} -> Tree (T Val) -> [E] Bool + , method insert : {type Val,E} -> Tree (T Val) -> + Key -> Val -> [E] Tree (T Val) + , method insert' : {type Val,E} -> Tree (T Val) -> + Key -> Val -> [E] (Pair (Tree (T Val)) Bool) + , method remove : {type Val,E} -> Tree (T Val) -> + Key -> [E] Tree (T Val) + , method remove' : {type Val,E} -> Tree (T Val) -> + Key -> [E] (Pair (Tree (T Val)) Bool) + , method member : {type Val,E} -> Tree (T Val) -> Key -> [E] Bool + , method find : {type Val,E} -> Tree (T Val) -> Key -> [E] Option Val + , method operate : {type Val,E} -> Tree (T Val) -> Key -> + (Unit -> [E] Option Val) -> (Val -> [E] Option Val) -> + [E] (Pair (Pair (Option Val) (Option Val)) (Tree (T Val))) + , method foldl : {type Val, type A,E} -> Tree (T Val) -> + (Key -> Val -> A -> [E] A) -> A -> [E] A + , method foldr : {type Val, type A,E} -> Tree (T Val) -> + (Key -> Val -> A -> [E] A) -> A -> [E] A + , method toList : {type Val,E} -> Tree (T Val) -> [E] List (Pair Key Val) + , method toValueList : {type Val,E} -> Tree (T Val) -> [E] List Val + , method domain : {type Val,E} -> Tree (T Val) -> [E] List Key + , method map : {type Val, type A,E} -> Tree (T Val) -> + (Val -> [E] A) -> [E] Tree (T A) + , method map2 : {type Val, type A,E} -> Tree (T Val) -> + (Key -> [E] A) -> [E] Tree (T A) +(* , method map3 : {type Val, type A,E} -> (Val -> [E] A) -> + Tree (T Val) -> [E] Tree (T A) *) + , method app : {type Val,E} -> Tree (T Val) -> + (Key -> Val -> [E] Unit) -> [] Unit + , method union : {type Val,E} -> Tree (T Val) -> Tree (T Val) -> + (Key -> Val -> Val -> [E] Val) -> [E] Tree (T Val) + , method partion : {type Val,E} -> Tree (T Val) -> Key -> + [E] (Pair (Pair (Tree (T Val)) (Option Val)) (Tree (T Val))) + , method partionLt : {type Val,E} -> Tree (T Val) -> Key -> + [E] Pair (Tree (T Val)) (Tree (T Val)) + , method partionGt : {type Val,E} -> Tree (T Val) -> Key -> + [E] Pair (Tree (T Val)) (Tree (T Val)) + , method rangeii : {type Val,E} -> Tree (T Val) -> Key -> Key -> + [E] Tree (T Val) + , method rangeie : {type Val,E} -> Tree (T Val) -> Key -> Key -> + [E] Tree (T Val) + , method rangeei : {type Val,E} -> Tree (T Val) -> Key -> Key -> + [E] Tree (T Val) + , method rangeee : {type Val,E} -> Tree (T Val) -> Key -> Key -> + [E] Tree (T Val) + , method least : {type Val,E} -> Tree (T Val) -> [E] Option (T Val) + , method greatest : {type Val,E} -> Tree (T Val) -> [E] Option (T Val) + , method leastGt : {type Val,E} -> Tree (T Val) -> Key -> [E] Option (T Val) + , method leastGeq : {type Val,E} -> Tree (T Val) -> Key -> [E] Option (T Val) + , method greatestLt : {type Val,E} -> Tree (T Val) -> + Key -> [E] Option (T Val) + , method greatestLeq : {type Val,E} -> Tree (T Val) -> + Key -> [E] Option (T Val) } diff --git a/lib/OrderedSetSignature.fram b/lib/OrderedSetSignature.fram index 45e9aebd..06fd90af 100644 --- a/lib/OrderedSetSignature.fram +++ b/lib/OrderedSetSignature.fram @@ -5,30 +5,30 @@ pub data OrderedSet Val = Set of { T , empty : T - , method isEmpty : T -> [] Bool - , singleton : Val -> [] T - , method insert : T -> Val -> [] T - , method remove : T -> Val -> [] T - , method singletonSet : Val -> [] T - , method member : T -> Val -> [] Bool - , method foldl : {type A} -> T -> (Val -> A -> [] A) -> A -> [] A - , method foldr : {type A} -> T -> (Val -> A -> [] A) -> A -> [] A - , method toList : T -> [] List Val - , method union : T -> T -> [] T - , method intersection : T -> T -> [] T - , method diffrence : T -> T -> [] T - , method eq : T -> T -> [] Bool - , method subset : T -> T -> [] Bool - , method partionLt : T -> Val -> [] (Pair T T) - , method partionGt : T -> Val -> [] (Pair T T) - , method rangeii : T -> Val -> Val -> [] T - , method rangeei : T -> Val -> Val -> [] T - , method rangeie : T -> Val -> Val -> [] T + , method isEmpty : {E} -> T -> [E] Bool + , singleton : {E} -> Val -> [E] T + , method insert : {E} -> T -> Val -> [E] T + , method remove : {E} -> T -> Val -> [E] T + , method singletonSet : {E} -> Val -> [E] T + , method member : {E} -> T -> Val -> [E] Bool + , method foldl : {type A,E} -> T -> (Val -> A -> [E] A) -> A -> [E] A + , method foldr : {type A,E} -> T -> (Val -> A -> [E] A) -> A -> [E] A + , method toList : {E} -> T -> [E] List Val + , method union : {E} -> T -> T -> [E] T + , method intersection : {E} -> T -> T -> [E] T + , method diffrence : {E} -> T -> T -> [E] T + , method eq : {E} -> T -> T -> [E] Bool + , method subset : {E} -> T -> T -> [E] Bool + , method partionLt : {E} -> T -> Val -> [E] (Pair T T) + , method partionGt : {E} -> T -> Val -> [E] (Pair T T) + , method rangeii : {E} -> T -> Val -> Val -> [E] T + , method rangeei : {E} -> T -> Val -> Val -> [E] T + , method rangeie : {E} -> T -> Val -> Val -> [E] T , method rangeee : T -> Val -> Val -> [] T - , method least : T -> [] Option Val - , method greatest : T -> [] Option Val - , method leastGt : T -> Val -> [] Option Val - , method leastGeq : T -> Val -> [] Option Val - , method greatestLt : T -> Val -> [] Option Val - , method greatestLeq : T -> Val -> [] Option Val + , method least : {E} -> T -> [E] Option Val + , method greatest : {E} -> T -> [E] Option Val + , method leastGt : {E} -> T -> Val -> [E] Option Val + , method leastGeq : {E} -> T -> Val -> [E] Option Val + , method greatestLt : {E} -> T -> Val -> [E] Option Val + , method greatestLeq : {E} -> T -> Val -> [E] Option Val } From 274f32458f051fe684842df7274da933cd37ff35 Mon Sep 17 00:00:00 2001 From: Jakub Chomiczewski Date: Tue, 29 Oct 2024 15:53:54 +0100 Subject: [PATCH 10/27] Changing from [E] in [|E] --- lib/OrderedMapSignature.fram | 68 ++++++++++++++++++------------------ lib/OrderedSetSignature.fram | 52 +++++++++++++-------------- 2 files changed, 60 insertions(+), 60 deletions(-) diff --git a/lib/OrderedMapSignature.fram b/lib/OrderedMapSignature.fram index 058ab79a..296c05d0 100644 --- a/lib/OrderedMapSignature.fram +++ b/lib/OrderedMapSignature.fram @@ -6,58 +6,58 @@ import open RedBlackTree pub data OrderedMap Key = Map of { T , empty : {type Val} -> Tree (T Val) - , singleton : {type Val} -> Key -> Val -> [] Tree (T Val) - , method isEmpty : {type Val,E} -> Tree (T Val) -> [E] Bool + , singleton : {type Val,E} -> Key -> Val -> [|E] Tree (T Val) + , method isEmpty : {type Val,E} -> Tree (T Val) -> [|E] Bool , method insert : {type Val,E} -> Tree (T Val) -> - Key -> Val -> [E] Tree (T Val) + Key -> Val -> [|E] Tree (T Val) , method insert' : {type Val,E} -> Tree (T Val) -> - Key -> Val -> [E] (Pair (Tree (T Val)) Bool) + Key -> Val -> [|E] (Pair (Tree (T Val)) Bool) , method remove : {type Val,E} -> Tree (T Val) -> - Key -> [E] Tree (T Val) + Key -> [|E] Tree (T Val) , method remove' : {type Val,E} -> Tree (T Val) -> - Key -> [E] (Pair (Tree (T Val)) Bool) - , method member : {type Val,E} -> Tree (T Val) -> Key -> [E] Bool - , method find : {type Val,E} -> Tree (T Val) -> Key -> [E] Option Val + Key -> [|E] (Pair (Tree (T Val)) Bool) + , method member : {type Val,E} -> Tree (T Val) -> Key -> [|E] Bool + , method find : {type Val,E} -> Tree (T Val) -> Key -> [|E] Option Val , method operate : {type Val,E} -> Tree (T Val) -> Key -> - (Unit -> [E] Option Val) -> (Val -> [E] Option Val) -> - [E] (Pair (Pair (Option Val) (Option Val)) (Tree (T Val))) + (Unit -> [|E] Option Val) -> (Val -> [|E] Option Val) -> + [|E] (Pair (Pair (Option Val) (Option Val)) (Tree (T Val))) , method foldl : {type Val, type A,E} -> Tree (T Val) -> - (Key -> Val -> A -> [E] A) -> A -> [E] A + (Key -> Val -> A -> [|E] A) -> A -> [|E] A , method foldr : {type Val, type A,E} -> Tree (T Val) -> - (Key -> Val -> A -> [E] A) -> A -> [E] A - , method toList : {type Val,E} -> Tree (T Val) -> [E] List (Pair Key Val) - , method toValueList : {type Val,E} -> Tree (T Val) -> [E] List Val - , method domain : {type Val,E} -> Tree (T Val) -> [E] List Key + (Key -> Val -> A -> [|E] A) -> A -> [|E] A + , method toList : {type Val,E} -> Tree (T Val) -> [|E] List (Pair Key Val) + , method toValueList : {type Val,E} -> Tree (T Val) -> [|E] List Val + , method domain : {type Val,E} -> Tree (T Val) -> [|E] List Key , method map : {type Val, type A,E} -> Tree (T Val) -> - (Val -> [E] A) -> [E] Tree (T A) + (Val -> [|E] A) -> [|E] Tree (T A) , method map2 : {type Val, type A,E} -> Tree (T Val) -> - (Key -> [E] A) -> [E] Tree (T A) -(* , method map3 : {type Val, type A,E} -> (Val -> [E] A) -> - Tree (T Val) -> [E] Tree (T A) *) + (Key -> [|E] A) -> [|E] Tree (T A) +(* , method map3 : {type Val, type A,E} -> (Val -> [|E] A) -> + Tree (T Val) -> [|E] Tree (T A) *) , method app : {type Val,E} -> Tree (T Val) -> - (Key -> Val -> [E] Unit) -> [] Unit + (Key -> Val -> [|E] Unit) -> [|E] Unit , method union : {type Val,E} -> Tree (T Val) -> Tree (T Val) -> - (Key -> Val -> Val -> [E] Val) -> [E] Tree (T Val) + (Key -> Val -> Val -> [|E] Val) -> [|E] Tree (T Val) , method partion : {type Val,E} -> Tree (T Val) -> Key -> - [E] (Pair (Pair (Tree (T Val)) (Option Val)) (Tree (T Val))) + [|E] (Pair (Pair (Tree (T Val)) (Option Val)) (Tree (T Val))) , method partionLt : {type Val,E} -> Tree (T Val) -> Key -> - [E] Pair (Tree (T Val)) (Tree (T Val)) + [|E] Pair (Tree (T Val)) (Tree (T Val)) , method partionGt : {type Val,E} -> Tree (T Val) -> Key -> - [E] Pair (Tree (T Val)) (Tree (T Val)) + [|E] Pair (Tree (T Val)) (Tree (T Val)) , method rangeii : {type Val,E} -> Tree (T Val) -> Key -> Key -> - [E] Tree (T Val) + [|E] Tree (T Val) , method rangeie : {type Val,E} -> Tree (T Val) -> Key -> Key -> - [E] Tree (T Val) + [|E] Tree (T Val) , method rangeei : {type Val,E} -> Tree (T Val) -> Key -> Key -> - [E] Tree (T Val) + [|E] Tree (T Val) , method rangeee : {type Val,E} -> Tree (T Val) -> Key -> Key -> - [E] Tree (T Val) - , method least : {type Val,E} -> Tree (T Val) -> [E] Option (T Val) - , method greatest : {type Val,E} -> Tree (T Val) -> [E] Option (T Val) - , method leastGt : {type Val,E} -> Tree (T Val) -> Key -> [E] Option (T Val) - , method leastGeq : {type Val,E} -> Tree (T Val) -> Key -> [E] Option (T Val) + [|E] Tree (T Val) + , method least : {type Val,E} -> Tree (T Val) -> [|E] Option (T Val) + , method greatest : {type Val,E} -> Tree (T Val) -> [|E] Option (T Val) + , method leastGt : {type Val,E} -> Tree (T Val) -> Key -> [|E] Option (T Val) + , method leastGeq : {type Val,E} -> Tree (T Val) -> Key -> [|E] Option (T Val) , method greatestLt : {type Val,E} -> Tree (T Val) -> - Key -> [E] Option (T Val) + Key -> [|E] Option (T Val) , method greatestLeq : {type Val,E} -> Tree (T Val) -> - Key -> [E] Option (T Val) + Key -> [|E] Option (T Val) } diff --git a/lib/OrderedSetSignature.fram b/lib/OrderedSetSignature.fram index 06fd90af..ebf51442 100644 --- a/lib/OrderedSetSignature.fram +++ b/lib/OrderedSetSignature.fram @@ -5,30 +5,30 @@ pub data OrderedSet Val = Set of { T , empty : T - , method isEmpty : {E} -> T -> [E] Bool - , singleton : {E} -> Val -> [E] T - , method insert : {E} -> T -> Val -> [E] T - , method remove : {E} -> T -> Val -> [E] T - , method singletonSet : {E} -> Val -> [E] T - , method member : {E} -> T -> Val -> [E] Bool - , method foldl : {type A,E} -> T -> (Val -> A -> [E] A) -> A -> [E] A - , method foldr : {type A,E} -> T -> (Val -> A -> [E] A) -> A -> [E] A - , method toList : {E} -> T -> [E] List Val - , method union : {E} -> T -> T -> [E] T - , method intersection : {E} -> T -> T -> [E] T - , method diffrence : {E} -> T -> T -> [E] T - , method eq : {E} -> T -> T -> [E] Bool - , method subset : {E} -> T -> T -> [E] Bool - , method partionLt : {E} -> T -> Val -> [E] (Pair T T) - , method partionGt : {E} -> T -> Val -> [E] (Pair T T) - , method rangeii : {E} -> T -> Val -> Val -> [E] T - , method rangeei : {E} -> T -> Val -> Val -> [E] T - , method rangeie : {E} -> T -> Val -> Val -> [E] T - , method rangeee : T -> Val -> Val -> [] T - , method least : {E} -> T -> [E] Option Val - , method greatest : {E} -> T -> [E] Option Val - , method leastGt : {E} -> T -> Val -> [E] Option Val - , method leastGeq : {E} -> T -> Val -> [E] Option Val - , method greatestLt : {E} -> T -> Val -> [E] Option Val - , method greatestLeq : {E} -> T -> Val -> [E] Option Val + , method isEmpty : {E} -> T -> [|E] Bool + , singleton : {E} -> Val -> [|E] T + , method insert : {E} -> T -> Val -> [|E] T + , method remove : {E} -> T -> Val -> [|E] T + , method singletonSet : {E} -> Val -> [|E] T + , method member : {E} -> T -> Val -> [|E] Bool + , method foldl : {type A,E} -> T -> (Val -> A -> [|E] A) -> A -> [|E] A + , method foldr : {type A,E} -> T -> (Val -> A -> [|E] A) -> A -> [|E] A + , method toList : {E} -> T -> [|E] List Val + , method union : {E} -> T -> T -> [|E] T + , method intersection : {E} -> T -> T -> [|E] T + , method diffrence : {E} -> T -> T -> [|E] T + , method eq : {E} -> T -> T -> [|E] Bool + , method subset : {E} -> T -> T -> [|E] Bool + , method partionLt : {E} -> T -> Val -> [|E] (Pair T T) + , method partionGt : {E} -> T -> Val -> [|E] (Pair T T) + , method rangeii : {E} -> T -> Val -> Val -> [|E] T + , method rangeei : {E} -> T -> Val -> Val -> [|E] T + , method rangeie : {E} -> T -> Val -> Val -> [|E] T + , method rangeee : {E} -> T -> Val -> Val -> [|E] T + , method least : {E} -> T -> [|E] Option Val + , method greatest : {E} -> T -> [|E] Option Val + , method leastGt : {E} -> T -> Val -> [|E] Option Val + , method leastGeq : {E} -> T -> Val -> [|E] Option Val + , method greatestLt : {E} -> T -> Val -> [|E] Option Val + , method greatestLeq : {E} -> T -> Val -> [|E] Option Val } From 858432245167dfe12653491d4be3a6a8472d2c8d Mon Sep 17 00:00:00 2001 From: Jakub Chomiczewski Date: Wed, 20 Nov 2024 14:25:21 +0100 Subject: [PATCH 11/27] Correcting style and renaming few things --- lib/Comparable.fram | 5 - lib/Map.fram | 335 +++++++++++++++++++++++++++++ lib/Ordered.fram | 4 +- lib/OrderedMap.fram | 252 ---------------------- lib/OrderedMapSignature.fram | 63 ------ lib/OrderedSet.fram | 232 -------------------- lib/OrderedSetSignature.fram | 34 --- lib/RedBlackTree.fram | 360 ++++++++++++++++++-------------- lib/Set.fram | 309 +++++++++++++++++++++++++++ test/stdlib/stdlib0001_Map.fram | 22 +- test/stdlib/stdlib0002_Set.fram | 18 +- 11 files changed, 866 insertions(+), 768 deletions(-) delete mode 100644 lib/Comparable.fram create mode 100644 lib/Map.fram delete mode 100644 lib/OrderedMap.fram delete mode 100644 lib/OrderedMapSignature.fram delete mode 100644 lib/OrderedSet.fram delete mode 100644 lib/OrderedSetSignature.fram create mode 100644 lib/Set.fram diff --git a/lib/Comparable.fram b/lib/Comparable.fram deleted file mode 100644 index 9bf47049..00000000 --- a/lib/Comparable.fram +++ /dev/null @@ -1,5 +0,0 @@ -(* This file is part of DBL, released under MIT license. - * See LICENSE for details. -*) - -pub data Comparable = Eq| Noteq diff --git a/lib/Map.fram b/lib/Map.fram new file mode 100644 index 00000000..256190d2 --- /dev/null +++ b/lib/Map.fram @@ -0,0 +1,335 @@ +(* This file is part of DBL, released under MIT license. + * See LICENSE for details. +*) + +import open RedBlackTree + +(** Signature *) + +pub data Map Key = Map of { + T + , empty : {type Val} -> Tree (T Val) + , method isEmpty : {type Val} -> Tree (T Val) -> [] Bool + , method insert : {type Val} -> Tree (T Val) -> + Key -> Val -> [] Tree (T Val) + , method insert' : {type Val} -> Tree (T Val) -> + Key -> Val -> [] (Pair (Tree (T Val)) Bool) + , method remove : {type Val} -> Tree (T Val) -> + Key -> [] Tree (T Val) + , method remove' : {type Val} -> Tree (T Val) -> + Key -> [] (Pair (Tree (T Val)) Bool) + , method member : {type Val} -> Tree (T Val) -> Key -> [] Bool + , method find : {type Val} -> Tree (T Val) -> Key -> [] Option Val + , method operate : {type Val,E} -> Tree (T Val) -> Key -> + (Unit -> [|E] Option Val) -> (Val -> [|E] Option Val) -> + [|E] (Pair (Pair (Option Val) (Option Val)) (Tree (T Val))) + , method foldl : {type Val, type A,E} -> Tree (T Val) -> + (Key -> Val -> A -> [|E] A) -> A -> [|E] A + , method foldr : {type Val, type A,E} -> Tree (T Val) -> + (Key -> Val -> A -> [|E] A) -> A -> [|E] A + , method toList : {type Val} -> Tree (T Val) -> [] List (Pair Key Val) + , method toValueList : {type Val} -> Tree (T Val) -> [] List Val + , method domain : {type Val} -> Tree (T Val) -> [] List Key + , method map : {type Val, type A,E} -> Tree (T Val) -> + (Val -> [|E] A) -> [|E] Tree (T A) + , method map2 : {type Val, type A,E} -> Tree (T Val) -> + (Key -> [|E] A) -> [|E] Tree (T A) + , method app : {type Val,E} -> Tree (T Val) -> + (Key -> Val -> [|E] Unit) -> [|E] Unit + , method union : {type Val,E} -> Tree (T Val) -> Tree (T Val) -> + (Key -> Val -> Val -> [|E] Val) -> [|E] Tree (T Val) + , method partion : {type Val} -> Tree (T Val) -> Key -> + [] (Pair (Pair (Tree (T Val)) (Option Val)) (Tree (T Val))) + , method partionLt : {type Val} -> Tree (T Val) -> Key -> + [] Pair (Tree (T Val)) (Tree (T Val)) + , method partionGt : {type Val} -> Tree (T Val) -> Key -> + [] Pair (Tree (T Val)) (Tree (T Val)) + , method range : {type Val} -> Tree (T Val) -> Interval Key -> + Interval Key -> [] Tree (T Val) + , method least : {type Val} -> Tree (T Val) -> [] Option (T Val) + , method greatest : {type Val} -> Tree (T Val) -> [] Option (T Val) + , method leastGt : {type Val} -> Tree (T Val) -> Key -> [] Option (T Val) + , method leastGeq : {type Val} -> Tree (T Val) -> Key -> [] Option (T Val) + , method greatestLt : {type Val} -> Tree (T Val) -> + Key -> [] Option (T Val) + , method greatestLeq : {type Val,E} -> Tree (T Val) -> + Key -> [] Option (T Val) +} + +(** implementation *) + +let isEmpty tree = + match tree with + | Leaf => True + | _ => False + end + +let insert compare tree key val = + match search (fn (key', _ ) => compare key key') tree [] with + | (Leaf, zipper) => zipRed (key,val) Leaf Leaf zipper + | ((Node {color, size = bulk, left, right}), zipper) => + zip (construct color bulk left (key,val) right) zipper + end + +let insert' compare tree key val = + match search (fn (key', _ ) => compare key key') tree [] with + | (Leaf, zipper) => (zipRed (key,val) Leaf Leaf zipper, False) + | ((Node {color, size = bulk, left, right}), zipper) => + (zip (construct color bulk left (key,val) right) zipper, True) + end + +let remove compare tree key = + match search (fn (key', _ ) => compare key key') tree [] with + | (Leaf,_) => tree + | (Node {color, left, right}, zipper) => + delete color left right zipper + end + +let remove' compare tree key = + match search (fn (key', _ ) => compare key key') tree [] with + | (Leaf,_) => (tree,False) + | (Node {color, left, right}, zipper) => + (delete color left right zipper, True) + end + +let rec member compare tree key = + match tree with + | Leaf => False + | Node {left, value = (key',_), right} => + match compare key key' with + | Less => member compare left key + | Equal => True + | Greater => member compare right key + end + end + +let rec find compare tree key = + match tree with + | Leaf => None + | Node {left, value = (key', val), right} => + match compare key key' with + | Less => find compare left key + | Equal => Some val + | Greater => find compare right key + end + end + +let rec operate compare tree key absentf presentf = + match search (fn (key', _ ) => compare key key') tree [] with + | (Leaf, zipper) => match absentf () with + | None => (None,None, tree) + | Some x => (None,Some x, zipRed (key,x) Leaf Leaf zipper) + end + | (Node {color, size = bulk, left, value = (_, val), right}, zipper) => + match presentf val with + | None => (Some val, None, delete color left right zipper) + | Some x => (Some val, Some x, zip + (construct color bulk left (key,x) right) zipper) + end + end + +let rec foldr func tree acc = + match tree with + | Leaf => acc + | Node {left, value = (key, val), right} => + let val_right = (foldr func right acc) in + let val_middle = (func key val val_right) in + foldr func left val_middle + end + +let mapFoldr tree func acc = foldr func tree acc + +let rec foldl func tree acc = + match tree with + | Leaf => acc + | Node {left, value = (key, val), right} => + let val_left = (foldl func left acc) in + let val_middle = (func key val val_left) in + foldl func right val_middle + end + +let mapFoldl tree func acc = foldl func tree acc + +let rec map tree func = match tree with + | Leaf => Leaf + | Node {color, size = bulk, left, value = (key,value), right} => + construct color bulk (map left func) (key,func value) (map right func) + end + +let rec map2 tree func = match tree with + | Leaf => Leaf + | Node {color, size = bulk, left, value = (key, _), right} => + construct color bulk (map2 left func) (key, func key) (map2 right func) + end + +let rec app tree func = match tree with + | Leaf => () + | Node {left, value = (key,value), right} => + let _ = app left func in + let _ = func key value in + app right func + end + +let rec union compare tree1 tree2 merge = + match tree1 with + | Leaf => tree2 + | Node {left = left1, value = (key1,value1), right = right1} => + match tree2 with + | Leaf => tree1 + | _ => let (output,left2,right2) = + split (fn (key2,_) => compare key1 key2) tree2 + in let new_pair = match output with + | None => (key1,value1) + | Some (_,value2) => (key1, merge key1 value1 value2) + end in joinVal (union compare left1 left2 merge) new_pair + (union compare right1 right2 merge) + end + end + +let partionLt compare tree key = + let (_,left,right) = split (fn (key2,_) => + match compare key key2 with + | Less => Less + | _ => Greater + end) tree in (left, right) + +let partionGt compare tree key = + let (_,left,right) = split (fn (key2,_) => + match compare key key2 with + | Greater => Greater + | _ => Less + end) tree in (left, right) + +let rec least tree = + match tree with + | Leaf => None + | Node {left = Leaf, value} => Some value + | Node {left} => least left + end + +let rec greatest tree = + match tree with + | Leaf => None + | Node { value, right=Leaf} => Some value + | Node {right} => greatest right + end + +let rec leastGt compare tree key = + match tree with + | Leaf => None + | Node {left, value = (key1, value), right} => + match compare key key1 with + | Less => match leastGt compare left key with + | None => Some (key1, value) + | x => x + end + | Equal => least right + | Greater => leastGt compare right key + end + end + +let rec leastGeq compare tree key = + match tree with + | Leaf => None + | Node {left, value = (key1, value), right} => + match compare key key1 with + | Less => match leastGeq compare left key with + | None => Some (key1,value) + | x => x + end + | Equal => Some (key1, value) + | Greater => leastGeq compare right key + end + end + +let rec greatestLt compare tree key = + match tree with + | Leaf => None + | Node {left, value = (key1,value), right} => + match compare key key1 with + | Less => greatestLt compare left key + | Equal => greatest left + | Greater => match greatestLt compare right key with + | None => Some (key1,value) + | x => x + end + end + end + +let rec greatestLeq compare tree key = + match tree with + | Leaf => None + | Node {left, value = (key1,value), right} => + match compare key key1 with + | Less => greatestLt compare left key + | Equal => Some (key1,value) + | Greater => match greatestLeq compare right key with + | None => Some (key1,value) + | x => x + end + end + end + +let toList tree = foldr (fn key value acc => (key, value) :: acc) tree [] + +let toValueList tree = foldr (fn key value acc => value :: acc) tree [] + +let domain tree = foldr (fn key value acc => key :: acc) tree [] + +let partion compare tree key = + let (output,left,right) = split (fn (key2,_) => compare key key2) tree + in match output with + | None => (left,None,right) + | Some (_,x) => (left,Some x, right) + end + +let range compare tree left right = + match (left,right) with + | (Inclusion left, Inclusion right) => + let (_,middle) = partionGt compare tree left in + let (result,_) = partionLt compare middle right in result + | (Inclusion left, Exclusion right) => + let (_,middle) = partionGt compare tree left in + let (result,_) = partionGt compare middle right in result + | (Exclusion left, Inclusion right) => + let (_,middle) = partionLt compare tree left in + let (result,_) = partionLt compare middle right in result + | (Exclusion left, Exclusion right) => + let (_,middle) = partionLt compare tree left in + let (result,_) = partionGt compare middle right in result + end + + + + +pub let make {Key} (compare : Key -> Key -> [] Ordered) = Map { + T = Pair Key + , empty = Leaf + , method isEmpty = isEmpty + , method insert = insert compare + , method insert' = insert' compare + , method remove = remove compare + , method remove' = remove' compare + , method member = member compare + , method find = find compare + , method operate = operate compare + , method foldl = mapFoldl + , method foldr = mapFoldr + , method toList = toList + , method toValueList = toValueList + , method domain = domain + , method map = map + , method map2 = map2 + , method app = app + , method union = union compare + , method partion = partion compare + , method partionLt = partionLt compare + , method partionGt = partionGt compare + , method range = range compare + , method least = least + , method greatest = greatest + , method leastGt = leastGt compare + , method leastGeq = leastGeq compare + , method greatestLt = greatestLt compare + , method greatestLeq = greatestLeq compare +} diff --git a/lib/Ordered.fram b/lib/Ordered.fram index e72f9455..dd45c213 100644 --- a/lib/Ordered.fram +++ b/lib/Ordered.fram @@ -2,13 +2,15 @@ * See LICENSE for details. *) -import open Comparable +pub data Comparable = Eq| Noteq pub data Ordered = | Less | Equal | Greater +pub data Interval Value = Inclusion of Value | Exclusion of Value + pub let ordToComp elem = match elem with | Equal => Eq | _ => Noteq end pub method toComparable {self : Ordered} = ordToComp self diff --git a/lib/OrderedMap.fram b/lib/OrderedMap.fram deleted file mode 100644 index bc658d68..00000000 --- a/lib/OrderedMap.fram +++ /dev/null @@ -1,252 +0,0 @@ -(* This file is part of DBL, released under MIT license. - * See LICENSE for details. -*) - -import open RedBlackTree -import open OrderedMapSignature - -let rec member compare tree key = - match tree with - | Leaf => False - | Node _ _ left (key',_) right => - match compare key key' with - | Less => member compare left key - | Equal => True - | Greater => member compare right key - end - end - -let rec find compare tree key = - match tree with - | Leaf => None - | Node _ _ left (key', val) right => - match compare key key' with - | Less => find compare left key - | Equal => Some val - | Greater => find compare right key - end - end - -let rec operate compare tree key absentf presentf = - match search (fn (key', _ ) => compare key key') tree [] with - | (Leaf, zipper) => match absentf () with - | None => (None,None, tree) - | Some x => (None,Some x, zipRed (key,x) Leaf Leaf zipper) - end - | (Node color bulk left (_, val) right, zipper) => - match presentf val with - | None => (Some val, None, delete color left right zipper) - | Some x => (Some val, Some x, zip - (Node color bulk left (key,x) right) zipper) - end - end - -let rec foldr func tree acc = - match tree with - | Leaf => acc - | Node _ _ left (key, val) right => - let val_right = (foldr func right acc) in - let val_middle = (func key val val_right) in - foldr func left val_middle - end - -let rec foldl func tree acc = - match tree with - | Leaf => acc - | Node _ _ left (key, val) right => - let val_left = (foldl func left acc) in - let val_middle = (func key val val_left) in - foldl func right val_middle - end - -let rec map tree func = match tree with - | Leaf => Leaf - | Node color bulk left (key,value) right => - Node color bulk (map left func) (key,func value) (map right func) - end - -let rec map2 tree func = match tree with - | Leaf => Leaf - | Node color bulk left (key, _) right => - Node color bulk (map2 left func) (key, func key) (map2 right func) - end - -let rec app tree func = match tree with - | Leaf => () - | Node _ _ left (key,value) right => - let _ = app left func in - let _ = func key value in - app right func - end - -let rec union compare tree1 tree2 merge = - match tree1 with - | Leaf => tree2 - | Node _ _ left1 (key1,value1) right1 => - match tree2 with - | Leaf => tree1 - | _ => let (output,left2,right2) = - split (fn (key2,_) => compare key1 key2) tree2 - in let new_pair = match output with - | None => (key1,value1) - | Some (_,value2) => (key1, merge key1 value1 value2) - end in join_val new_pair (union compare left1 left2 merge) - (union compare right1 right2 merge) - end - end - -let partionLt compare tree key = - let (_,left,right) = split (fn (key2,_) => - match compare key key2 with - | Less => Less - | _ => Greater - end) tree in (left, right) - -let partionGt compare tree key = - let (_,left,right) = split (fn (key2,_) => - match compare key key2 with - | Greater => Greater - | _ => Less - end) tree in (left, right) - -let rec least tree = - match tree with - | Leaf => None - | Node _ _ Leaf res _ => Some res - | Node _ _ left _ _ => least left - end - -let rec greatest tree = - match tree with - | Leaf => None - | Node _ _ _ res Leaf => Some res - | Node _ _ _ res right => greatest right - end - -let rec leastGt compare tree key = - match tree with - | Leaf => None - | Node _ _ left (key1, value) right => - match compare key key1 with - | Less => match leastGt compare left key with - | None => Some (key1, value) - | x => x - end - | Equal => least right - | Greater => leastGt compare right key - end - end - -let rec leastGeq compare tree key = - match tree with - | Leaf => None - | Node _ _ left (key1, value) right => - match compare key key1 with - | Less => match leastGeq compare left key with - | None => Some (key1,value) - | x => x - end - | Equal => Some (key1, value) - | Greater => leastGeq compare right key - end - end - -let rec greatestLt compare tree key = - match tree with - | Leaf => None - | Node _ _ left (key1,value) right => - match compare key key1 with - | Less => greatestLt compare left key - | Equal => greatest left - | Greater => match greatestLt compare right key with - | None => Some (key1,value) - | x => x - end - end - end - -let rec greatestLeq compare tree key = - match tree with - | Leaf => None - | Node _ _ left (key1,value) right => - match compare key key1 with - | Less => greatestLt compare left key - | Equal => Some (key1,value) - | Greater => match greatestLeq compare right key with - | None => Some (key1,value) - | x => x - end - end - end - -pub let makeOrderedMap {Key} (compare : Key -> Key -> [] Ordered) = Map { - T = Pair Key - , empty = Leaf - , singleton = fn key val => Node Black 1 Leaf (key,val) Leaf - , method isEmpty = fn tree => match tree with | Leaf => True | _ => False end - , method insert = fn tree key val => - match search (fn (key', _ ) => compare key key') tree [] with - | (Leaf, zipper) => zipRed (key,val) Leaf Leaf zipper - | ((Node color bulk left _ right), zipper) => - zip (Node color bulk left (key,val) right) zipper - end - , method insert' = fn tree key val => - match search (fn (key', _ ) => compare key key') tree [] with - | (Leaf, zipper) => (zipRed (key,val) Leaf Leaf zipper, False) - | ((Node color bulk left _ right), zipper) => - (zip (Node color bulk left (key,val) right) zipper, True) - end - , method remove = fn tree key => - match search (fn (key', _ ) => compare key key') tree [] with - | (Leaf,_) => tree - | (Node color _ left _ right, zipper) => - delete color left right zipper - end - , method remove' = fn tree key => - match search (fn (key', _ ) => compare key key') tree [] with - | (Leaf,_) => (tree,False) - | (Node color _ left _ right, zipper) => - (delete color left right zipper, True) - end - , method member = member compare - , method find = find compare - , method operate = operate compare - , method foldl = fn tree func acc => foldl func tree acc - , method foldr = fn tree func acc => foldr func tree acc - , method toList = fn tree => - foldr (fn key value acc => (key, value) :: acc) tree [] - , method toValueList = fn tree => - foldr (fn key value acc => value :: acc) tree [] - , method domain = fn tree => - foldr (fn key value acc => key :: acc) tree [] - , method map = fn tree func => map tree func - , method map2 = map2 - , method app = app - , method union = union compare - , method partion = fn tree key => - let (output,left,right) = split (fn (key2,_) => compare key key2) tree - in match output with - | None => (left,None,right) - | Some (_,x) => (left,Some x, right) - end - , method partionLt = partionLt compare - , method partionGt = partionGt compare - , method rangeee = fn tree left right => - let (_,middle) = partionLt compare tree left in - let (result,_) = partionGt compare middle right in result - , method rangeei = fn tree left right => - let (_,middle) = partionLt compare tree left in - let (result,_) = partionLt compare middle right in result - , method rangeie = fn tree left right => - let (_,middle) = partionGt compare tree left in - let (result,_) = partionGt compare middle right in result - , method rangeii = fn tree left right => - let (_,middle) = partionGt compare tree left in - let (result,_) = partionLt compare middle right in result - , method least = least - , method greatest = greatest - , method leastGt = leastGt compare - , method leastGeq = leastGeq compare - , method greatestLt = greatestLt compare - , method greatestLeq = greatestLeq compare -} diff --git a/lib/OrderedMapSignature.fram b/lib/OrderedMapSignature.fram deleted file mode 100644 index 296c05d0..00000000 --- a/lib/OrderedMapSignature.fram +++ /dev/null @@ -1,63 +0,0 @@ -(* This file is part of DBL, released under MIT license. - * See LICENSE for details. -*) -import open RedBlackTree - -pub data OrderedMap Key = Map of { - T - , empty : {type Val} -> Tree (T Val) - , singleton : {type Val,E} -> Key -> Val -> [|E] Tree (T Val) - , method isEmpty : {type Val,E} -> Tree (T Val) -> [|E] Bool - , method insert : {type Val,E} -> Tree (T Val) -> - Key -> Val -> [|E] Tree (T Val) - , method insert' : {type Val,E} -> Tree (T Val) -> - Key -> Val -> [|E] (Pair (Tree (T Val)) Bool) - , method remove : {type Val,E} -> Tree (T Val) -> - Key -> [|E] Tree (T Val) - , method remove' : {type Val,E} -> Tree (T Val) -> - Key -> [|E] (Pair (Tree (T Val)) Bool) - , method member : {type Val,E} -> Tree (T Val) -> Key -> [|E] Bool - , method find : {type Val,E} -> Tree (T Val) -> Key -> [|E] Option Val - , method operate : {type Val,E} -> Tree (T Val) -> Key -> - (Unit -> [|E] Option Val) -> (Val -> [|E] Option Val) -> - [|E] (Pair (Pair (Option Val) (Option Val)) (Tree (T Val))) - , method foldl : {type Val, type A,E} -> Tree (T Val) -> - (Key -> Val -> A -> [|E] A) -> A -> [|E] A - , method foldr : {type Val, type A,E} -> Tree (T Val) -> - (Key -> Val -> A -> [|E] A) -> A -> [|E] A - , method toList : {type Val,E} -> Tree (T Val) -> [|E] List (Pair Key Val) - , method toValueList : {type Val,E} -> Tree (T Val) -> [|E] List Val - , method domain : {type Val,E} -> Tree (T Val) -> [|E] List Key - , method map : {type Val, type A,E} -> Tree (T Val) -> - (Val -> [|E] A) -> [|E] Tree (T A) - , method map2 : {type Val, type A,E} -> Tree (T Val) -> - (Key -> [|E] A) -> [|E] Tree (T A) -(* , method map3 : {type Val, type A,E} -> (Val -> [|E] A) -> - Tree (T Val) -> [|E] Tree (T A) *) - , method app : {type Val,E} -> Tree (T Val) -> - (Key -> Val -> [|E] Unit) -> [|E] Unit - , method union : {type Val,E} -> Tree (T Val) -> Tree (T Val) -> - (Key -> Val -> Val -> [|E] Val) -> [|E] Tree (T Val) - , method partion : {type Val,E} -> Tree (T Val) -> Key -> - [|E] (Pair (Pair (Tree (T Val)) (Option Val)) (Tree (T Val))) - , method partionLt : {type Val,E} -> Tree (T Val) -> Key -> - [|E] Pair (Tree (T Val)) (Tree (T Val)) - , method partionGt : {type Val,E} -> Tree (T Val) -> Key -> - [|E] Pair (Tree (T Val)) (Tree (T Val)) - , method rangeii : {type Val,E} -> Tree (T Val) -> Key -> Key -> - [|E] Tree (T Val) - , method rangeie : {type Val,E} -> Tree (T Val) -> Key -> Key -> - [|E] Tree (T Val) - , method rangeei : {type Val,E} -> Tree (T Val) -> Key -> Key -> - [|E] Tree (T Val) - , method rangeee : {type Val,E} -> Tree (T Val) -> Key -> Key -> - [|E] Tree (T Val) - , method least : {type Val,E} -> Tree (T Val) -> [|E] Option (T Val) - , method greatest : {type Val,E} -> Tree (T Val) -> [|E] Option (T Val) - , method leastGt : {type Val,E} -> Tree (T Val) -> Key -> [|E] Option (T Val) - , method leastGeq : {type Val,E} -> Tree (T Val) -> Key -> [|E] Option (T Val) - , method greatestLt : {type Val,E} -> Tree (T Val) -> - Key -> [|E] Option (T Val) - , method greatestLeq : {type Val,E} -> Tree (T Val) -> - Key -> [|E] Option (T Val) -} diff --git a/lib/OrderedSet.fram b/lib/OrderedSet.fram deleted file mode 100644 index 1b854424..00000000 --- a/lib/OrderedSet.fram +++ /dev/null @@ -1,232 +0,0 @@ -(* This file is part of DBL, released under MIT license. - * See LICENSE for details. -*) - -import open RedBlackTree -import open OrderedSetSignature - -data rec Q Val = Nil | E of Val , Q Val | T of Tree Val , Q Val - -let rec eqMain eq qs1 qs2 = - match (qs1,qs2) with - | (Nil,Nil) => True - | (Nil, E _ _) => False - | (E _ _, Nil) => False - | (T Leaf rest, _) => eqMain eq rest qs2 - | (_, T Leaf rest) => eqMain eq qs1 rest - | (T (Node _ _ left elem right) rest, _) => - eqMain eq (T left (E elem (T right rest))) qs2 - | (_, T (Node _ _ left elem right) rest) => - eqMain eq qs1 (T left (E elem (T right rest))) - | (E elem1 rest1, E elem2 rest2) => - match eq elem1 elem2 with - | Noteq => False - | Eq => eqMain eq rest1 rest2 - end - end - -let rec subsetMain comp qs1 qs2 = - match (qs1,qs2) with - | (Nil,_) => True - | (E _ _ , Nil) => False - | (T Leaf rest, _) => subsetMain comp rest qs2 - | (_ , T Leaf rest) => subsetMain comp qs1 rest - | (T (Node _ _ left elem right) rest, _) => - subsetMain comp (T left (E elem (T right rest))) qs2 - | (_, T (Node _ _ left elem right) rest) => - subsetMain comp qs1 (T left (E elem (T right rest))) - | (E elem1 rest1, E elem2 rest2) => - match comp elem1 elem2 with - | Less => False - | Equal => subsetMain comp rest1 rest2 - | Greater => subsetMain comp qs1 rest2 - end - end - -let partionLt compare = fn tree key1 => let (_,left,right) = - split (fn key2 => match compare key1 key2 with - | Greater => Greater | _ => Less end) tree in (left,right) - -let partionGt compare = fn tree key1 => let (_, left,right) = - split (fn key2 => match compare key1 key2 with - | Less => Less | _ => Greater end) tree in (left,right) - -let rec least tree = - match tree with - | Leaf => None - | Node _ _ Leaf x _ => Some x - | Node _ _ left _ _ => least left - end - -let rec greatest tree = - match tree with - | Leaf => None - | Node _ _ _ x Leaf => Some x - | Node _ _ _ _ right => greatest right - end - -pub let makeOrderedSet {Val} (compare : Val -> Val -> [] Ordered) = Set { - T = Tree Val - , empty = Leaf - , method isEmpty = - (fn tree => match tree with - | Leaf => True - | _ => False - end) - , method singletonSet = fn elem => Node Black 1 Leaf elem Leaf - , singleton = fn elem => Node Black 1 Leaf elem Leaf - , method insert = fn tree elem => - match search (fn val => compare elem val) tree [] with - | (Leaf,zipper) => zipRed elem Leaf Leaf zipper - | (Node _ _ _ _ _,_) => tree - end - , method remove = fn tree elem => - match search (fn val => compare elem val) tree [] with - | (Leaf,_) => tree - | (Node color _ left _ right,zipper) => delete color left right zipper - end - , method member = fn tree elem => let rec search tree elem = - match tree with - | Leaf => False - | Node _ _ left val right => - match compare elem val with - | Less => search left elem - | Greater => search right elem - | Equal => True - end - end in search tree elem - , method foldl = fn tree func acc => let rec foldl tree func acc = - match tree with - | Leaf => acc - | Node _ _ left val right => - foldl right func (func val (foldl left func acc)) - end in foldl tree func acc - , method foldr = fn tree func acc => let rec foldr tree func acc = - match tree with - | Leaf => acc - | Node _ _ left val right => - foldr left func (func val (foldr right func acc)) - end in foldr tree func acc - , method toList = fn tree => let rec toList tree acc = - match tree with - | Leaf => acc - | Node _ _ left val right => - toList left (val :: toList right acc) - end in toList tree [] - , method union = fn tree1 tree2 => let rec union tree1 tree2 = - match tree1 with - | Leaf => tree2 - | Node _ _ left1 key1 right1 => - match tree2 with - | Leaf => tree1 - | Node _ _ _ _ _ => - let (_,left2,right2) = split (fn key2 => compare key1 key2) tree2 - in join_val key1 (union left1 left2) (union right1 right2) - end - end in union tree1 tree2 - , method intersection = fn tree1 tree2 => let rec intersection tree1 tree2 = - match tree1 with - | Leaf => Leaf - | Node _ _ left1 key1 right1 => - match tree2 with - | Leaf => Leaf - | _ => let (value_out, left2, right2) = - split (fn key2 => compare key1 key2) tree2 - in let left = intersection left1 left2 - in let right = intersection right1 right2 - in match value_out with - | Some _ => join_val key1 left right - | None => join left right - end - end - end in intersection tree1 tree2 - , method diffrence = fn tree1 tree2 => let rec diffrence tree1 tree2 = - match tree1 with - | Leaf => Leaf - | Node _ _ left1 key1 right1 => - match tree2 with - | Leaf => tree1 - | _ => let (value_out, left2, right2) = - split (fn key2 => compare key1 key2) tree2 - in let left = diffrence left1 left2 - in let right = diffrence right1 right2 - in match value_out with - | Some _ => join left right - | None => join_val key1 left right - end - end - end in diffrence tree1 tree2 - , method eq = fn set1 set2 => - eqMain (fn e1 e2 => (compare e1 e2).toComparable) (T set1 Nil) (T set2 Nil) - , method subset = fn set1 set2 => subsetMain compare (T set1 Nil) (T set2 Nil) - , method partionLt = partionLt compare - , method partionGt = partionGt compare - , method rangeii = fn tree left right => - let (_, tree') = partionLt compare tree left in - let (tree'',_) = partionGt compare tree' right in tree'' - , method rangeei = fn tree left right => - let (_, tree') = partionGt compare tree left in - let (tree'',_) = partionGt compare tree' right in tree'' - , method rangeie = fn tree left right => - let (_, tree') = partionLt compare tree left in - let (tree'',_) = partionLt compare tree' right in tree'' - , method rangeee = fn tree left right => - let (_, tree') = partionGt compare tree left in - let (tree'',_) = partionLt compare tree' right in tree'' - , method least = fn tree => least tree - , method greatest = fn tree => greatest tree - , method leastGt = fn tree val => let rec leastGt tree val = - match tree with - | Leaf => None - | Node _ _ left key right => - match compare val key with - | Less => let x = leastGt left val in - match x with - | None => Some key - | _ => x - end - | Equal => least right - | Greater => leastGt right val - end - end in leastGt tree val - , method leastGeq = fn tree val => let rec leastGeq tree val = - match tree with - | Leaf => None - | Node _ _ left key right => - match compare val key with - | Less => match leastGeq left val with - | None => Some key - | x => x - end - | Equal => Some val - | Greater => leastGeq right val - end - end in leastGeq tree val - , method greatestLt = fn tree val => let rec greatestLt tree val = - match tree with - | Leaf => None - | Node _ _ left key right => - match compare val key with - | Less => greatestLt left val - | Equal => greatest left - | Greater => match greatestLt right val with - | None => Some key - | x => x - end - end - end in greatestLt tree val - , method greatestLeq = fn tree val => - let rec greatestLeq tree val = - match tree with - | Leaf => None - | Node _ _ left key right => - match compare val key with - | Less => greatestLeq left val - | Equal => Some val - | Greater => match greatestLeq right val with - | None => Some key - | x => x - end - end - end in greatestLeq tree val -} diff --git a/lib/OrderedSetSignature.fram b/lib/OrderedSetSignature.fram deleted file mode 100644 index ebf51442..00000000 --- a/lib/OrderedSetSignature.fram +++ /dev/null @@ -1,34 +0,0 @@ -(* This file is part of DBL, released under MIT license. - * See LICENSE for details. -*) - -pub data OrderedSet Val = Set of { - T - , empty : T - , method isEmpty : {E} -> T -> [|E] Bool - , singleton : {E} -> Val -> [|E] T - , method insert : {E} -> T -> Val -> [|E] T - , method remove : {E} -> T -> Val -> [|E] T - , method singletonSet : {E} -> Val -> [|E] T - , method member : {E} -> T -> Val -> [|E] Bool - , method foldl : {type A,E} -> T -> (Val -> A -> [|E] A) -> A -> [|E] A - , method foldr : {type A,E} -> T -> (Val -> A -> [|E] A) -> A -> [|E] A - , method toList : {E} -> T -> [|E] List Val - , method union : {E} -> T -> T -> [|E] T - , method intersection : {E} -> T -> T -> [|E] T - , method diffrence : {E} -> T -> T -> [|E] T - , method eq : {E} -> T -> T -> [|E] Bool - , method subset : {E} -> T -> T -> [|E] Bool - , method partionLt : {E} -> T -> Val -> [|E] (Pair T T) - , method partionGt : {E} -> T -> Val -> [|E] (Pair T T) - , method rangeii : {E} -> T -> Val -> Val -> [|E] T - , method rangeei : {E} -> T -> Val -> Val -> [|E] T - , method rangeie : {E} -> T -> Val -> Val -> [|E] T - , method rangeee : {E} -> T -> Val -> Val -> [|E] T - , method least : {E} -> T -> [|E] Option Val - , method greatest : {E} -> T -> [|E] Option Val - , method leastGt : {E} -> T -> Val -> [|E] Option Val - , method leastGeq : {E} -> T -> Val -> [|E] Option Val - , method greatestLt : {E} -> T -> Val -> [|E] Option Val - , method greatestLeq : {E} -> T -> Val -> [|E] Option Val -} diff --git a/lib/RedBlackTree.fram b/lib/RedBlackTree.fram index a0fd992b..83b0eb5c 100644 --- a/lib/RedBlackTree.fram +++ b/lib/RedBlackTree.fram @@ -5,160 +5,197 @@ import open Ordered import List -pub rec - data Color = - | Red - | Black - data Tree Value = - | Leaf - | Node of Color, Int, Tree Value, Value, Tree Value - data ZipElem Value = - | Left of Color, Value, Tree Value - | Right of Color, Value, Tree Value -end +data Color = + | Red + | Black +pub data rec Tree Value = + | Leaf + | Node of {color: Color, + size: Int, + left: Tree Value, + value: Value, + right: Tree Value} +data ZipElem Value = + | Left of Color, Value, Tree Value + | Right of Color, Tree Value, Value pub let empty = Leaf pub let size tree = match tree with | Leaf => 0 - | Node _ bulk _ _ _ => bulk + | Node {size} => size end pub let makeNode color left value right = - Node color (size left + size right + 1) left value right + Node {color, size = size left + size right + 1, left, value, right} + +pub let construct color size left value right = + Node {color,size,left,value,right} pub let rec zip tree zipper = match zipper with | [] => tree - | Left color value right :: rest => zip (makeNode color tree value right) rest + | Left color value right :: rest => + zip (makeNode color tree value right) rest - | Right color value left :: rest => zip (makeNode color left value tree) rest + | Right color left value :: rest => + zip (makeNode color left value tree) rest end pub let rec zipRed value left right zipper = match zipper with - | [] => makeNode Black left value right - - | Left Black value1 right1 :: rest => - zip (makeNode Black (makeNode Red left value right) value1 right1) rest - - | Right Black value1 left1 :: rest => - zip (makeNode Black left1 value1 (makeNode Red left value right)) rest - - | Left Red value1 right1 :: - Left _ value2 (Node Red bulk3 left3 value3 right3) :: - rest => zipRed value2 - (makeNode Black (makeNode Red left value right) value1 right1) - (Node Black bulk3 left3 value3 right3) rest - - | Left Red value1 right1 :: - Right _ value2 (Node Red bulk3 left3 value3 right3) :: - rest => zipRed value2 - (Node Black bulk3 left3 value3 right3) - (makeNode Black (makeNode Red left value right) value1 right1) rest - - | Right Red value1 left1 :: - Left _ value2 (Node Red bulk3 left3 value3 right3) :: - rest => zipRed value2 - (makeNode Black left1 value1 (makeNode Red left value right)) - (Node Black bulk3 left3 value3 right3) rest - - | Right Red value1 left1 :: - Right _ value2 (Node Red bulk3 left3 value3 right3) :: - rest => zipRed value2 (Node Black bulk3 left3 value3 right3) - (makeNode Black left1 value1 (makeNode Red left value right)) rest - - | Left Red value1 right1 :: - Left _ value2 node3 :: - rest => zip (makeNode Black (makeNode Red left value right) value1 - (makeNode Red right1 value2 node3)) rest - - | Left Red value1 right1 :: - Right _ value2 node3 :: - rest => zip (makeNode Black (makeNode Red node3 value2 left) - value (makeNode Red right value1 right1)) rest - - | Right Red value1 left1 :: - Left _ value2 node3 :: - rest => zip (makeNode Black (makeNode Red left1 value1 left) - value (makeNode Red right value2 node3)) rest - - | Right Red value1 left1 :: - Right _ value2 node3 :: - rest => zip (makeNode Black (makeNode Red node3 value2 left1) - value1 (makeNode Red left value right)) rest - - | Left Red value1 right1 :: - [] => makeNode Black (makeNode Red left value right) value1 right1 - - | Right Red value1 left1 :: - [] => makeNode Black left1 value1 (makeNode Red left value right) + |[] => makeNode Black left value right + + |Left Black value1 right1 :: rest => + zip (makeNode Black (makeNode Red left value right) value1 right1) rest + + | Right Black left1 value1 :: rest => + zip (makeNode Black left1 value1 (makeNode Red left value right)) rest + + |Left Red value1 right1 :: + Left _ value2 + (Node {color = Red, size = bulk3, left = left3, + value = value3, right = right3}) :: rest => + zipRed value2 + (makeNode Black (makeNode Red left value right) value1 right1) + (construct Black bulk3 left3 value3 right3) rest + + |Left Red value1 right1 :: + Right _ + (Node {color = Red, size = bulk3, left = left3, + value = value3, right = right3}) value2 :: rest => + zipRed value2 + (construct Black bulk3 left3 value3 right3) + (makeNode Black (makeNode Red left value right) value1 right1) rest + + |Right Red left1 value1 :: + Left _ value2 + (Node {color = Red, size = bulk3, left = left3, + value = value3, right = right3}) :: rest => + zipRed value2 + (makeNode Black left1 value1 (makeNode Red left value right)) + (construct Black bulk3 left3 value3 right3) rest + + |Right Red left1 value1 :: + Right _ (Node {color = Red, size = bulk3, left = left3, + value = value3, right = right3}) value2 :: rest => + zipRed value2 + (construct Black bulk3 left3 value3 right3) + (makeNode Black left1 value1 (makeNode Red left value right)) rest + + |Left Red value1 right1 :: + Left _ value2 node3 :: rest => + zip + (makeNode Black (makeNode Red left value right) value1 + (makeNode Red right1 value2 node3)) rest + + |Left Red value1 right1 :: + Right _ node3 value2 :: rest => + zip + (makeNode Black (makeNode Red node3 value2 left) + value (makeNode Red right value1 right1)) rest + + |Right Red left1 value1 :: + Left _ value2 node3 :: rest => + zip + (makeNode Black (makeNode Red left1 value1 left) + value (makeNode Red right value2 node3)) rest + + |Right Red left1 value1 :: + Right _ node3 value2 :: rest => + zip + (makeNode Black (makeNode Red node3 value2 left1) + value1 (makeNode Red left value right)) rest + + |Left Red value1 right1 :: + [] => makeNode Black (makeNode Red left value right) value1 right1 + + |Right Red left1 value1 :: + [] => makeNode Black left1 value1 (makeNode Red left value right) end pub let rec zipBlack tree zipper = match zipper with - | [] => tree - - | Left color1 value1 (Node _ _ left2 value2 - (Node Red bulk3 left3 value3 right3)) - :: rest => zip (makeNode color1 (makeNode Black tree value1 left2 ) value2 - (Node Black bulk3 left3 value3 right3)) rest - - | Right color1 value1 (Node _ _ (Node Red bulk3 left3 value3 right3) - value2 right2) :: rest => zip (makeNode color1 - (Node Black bulk3 left3 value3 right3) value2 - (makeNode Black right2 value1 tree)) rest - - | Left color1 value1 (Node _ _ (Node Red _ left3 value3 right3) - value2 right2) :: rest => zip (makeNode color1 - (makeNode Black tree value1 left3) value3 + |[] => tree + + |Left color1 value1 + (Node {left = left2, value = value2, + right = (Node {color = Red, size = bulk3, + left = left3, value = value3, right = right3})}) :: + rest => + zip + (makeNode color1 (makeNode Black tree value1 left2 ) value2 + (construct Black bulk3 left3 value3 right3)) rest + + |Right color1 (Node { left = (Node {color = Red, size = bulk3, left = left3, + value = value3, right = right3}), value = value2, right = right2}) + value1 :: rest => + zip + (makeNode color1 (construct Black bulk3 left3 value3 right3) value2 + (makeNode Black right2 value1 tree)) rest + + |Left color1 value1 (Node {left = (Node {color = Red, left = left3, + value = value3, right = right3}), value = value2, right = right2}) :: rest => + zip + (makeNode color1 (makeNode Black tree value1 left3) value3 (makeNode Black right3 value2 right2)) rest - | Right color1 value1 (Node _ _ left2 value2 (Node Red _ left3 value3 - right3)) :: rest => zip (makeNode color1 (makeNode Black left2 value2 left3) - value3 (makeNode Black right3 value1 tree)) rest - - | Left Red value1 (Node _ bulk2 left2 value2 right2) - :: rest => zip (makeNode Black tree value1 - (Node Red bulk2 left2 value2 right2)) rest - - | Right Red value1 (Node _ bulk2 left2 value2 right2) - :: rest => zip (makeNode Black (Node Red bulk2 left2 value2 right2) - value1 tree) rest - - | Left Black value1 (Node Black bulk2 left2 value2 right2) - :: rest => zipBlack (makeNode Black tree value1 - (Node Red bulk2 left2 value2 right2)) rest - - | Right Black value1 (Node Black bulk2 left2 value2 right2) - :: rest => zipBlack (makeNode Black (Node Red bulk2 left2 value2 - right2) value1 tree) rest - - | Left Black value1 (Node Red _ left2 value2 right2) :: rest - => zipBlack tree (Left Red value1 left2 :: Left Black - value2 right2 :: rest) - - | Right Black value1 (Node Red _ left2 value2 right2) :: rest - => zipBlack tree (Right Red value1 right2 :: Right Black - value2 left2 :: rest) - - | Left _ _ Leaf :: _ => tree - - | Right _ _ Leaf :: _ => tree + |Right color1 (Node {left = left2, value = value2, right = + (Node {color = Red,left = left3, value = value3, right = right3})}) + value1 :: rest => + zip (makeNode color1 (makeNode Black left2 value2 left3) + value3 (makeNode Black right3 value1 tree)) rest + + |Left Red value1 (Node {size = bulk2, left = left2, + value = value2, right=right2}) :: rest => + zip + (makeNode Black tree value1 (construct Red bulk2 left2 value2 right2)) rest + + |Right Red (Node {size = bulk2, left = left2, + value = value2, right = right2}) value1 :: rest => + zip + (makeNode Black (construct Red bulk2 left2 value2 right2) value1 tree) rest + + |Left Black value1 (Node {color = Black, size = bulk2, left = left2, + value = value2,right = right2}) :: rest => + zipBlack + (makeNode Black tree value1 (construct Red bulk2 left2 value2 right2)) rest + + |Right Black (Node {color = Black, size = bulk2, left = left2, + value = value2, right = right2}) value1 :: rest => + zipBlack + (makeNode Black (construct Red bulk2 left2 value2 right2) value1 tree) rest + + |Left Black value1 (Node {color = Red, left = left2, + value = value2, right = right2}) :: rest => + zipBlack + tree (Left Red value1 left2 :: Left Black value2 right2 :: rest) + + |Right Black (Node {color = Red, left = left2, value = value2, + right = right2}) value1 :: rest => + zipBlack + tree (Right Red right2 value1 :: Right Black left2 value2 :: rest) + + //Impossible + | Left _ _ Leaf :: _ => tree + + | Right _ Leaf _ :: _ => tree end pub let rec search func tree zipper = match tree with | Leaf => (Leaf, zipper) - | Node color _ left value right => + | Node {color, size=_, left, value, right} => match func value with - | Less => search func left (Left color value right :: zipper) - | Greater => search func right (Right color value left :: zipper) + | Less => + search func left (Left color value right :: zipper) + | Greater => + search func right (Right color left value :: zipper) | Equal => (tree, zipper) end end @@ -166,113 +203,122 @@ pub let rec search func tree zipper = pub let rec searchMin tree zipper = match tree with | Leaf => zipper - | Node color _ left value right => - searchMin left (Left color value right :: zipper) + | Node {color,size=_,left,value,right} => + searchMin left (Left color value right :: zipper) end pub let rec searchMax tree zipper = match tree with | Leaf => zipper - | Node color _ left value right => - searchMax right (Right color value left :: zipper) + | Node {color,size=_, left, value, right} => + searchMax right (Right color left value:: zipper) end pub let deleteNearLeaf color child zipper = match color with | Red => zip Leaf zipper | Black => match child with - | Node _ _ _ value _ => zip (makeNode Black Leaf value Leaf) zipper + | Node {value} => + zip (makeNode Black Leaf value Leaf) zipper | Leaf => zipBlack Leaf zipper end end pub let delete color left right zipper = match right with - | Leaf => match left with + | Leaf => + match left with | Leaf => match color with | Red => zip Leaf zipper | Black => zipBlack Leaf zipper end - | _ => match searchMax left [] with - | Right colorLeftMin valueLeftMin leftLeftMin :: zipperr - => deleteNearLeaf colorLeftMin leftLeftMin - (List.append zipperr (Left color valueLeftMin right :: zipper)) + | _ => + match searchMax left [] with + | Right colorLeftMin leftLeftMin valueLeftMin :: zipperr => + deleteNearLeaf colorLeftMin leftLeftMin + (List.append zipperr (Left color valueLeftMin right :: zipper)) | _ => Leaf end end - | _ => match searchMin right [] with - | Left colorRightMin valueRightMin rightRightMin :: zipperr - => deleteNearLeaf colorRightMin rightRightMin - (List.append zipperr (Right color valueRightMin left :: zipper)) + | _ => + match searchMin right [] with + | Left colorRightMin valueRightMin rightRightMin :: zipperr => + deleteNearLeaf colorRightMin rightRightMin + (List.append zipperr (Right color left valueRightMin :: zipper)) | _ => Leaf end end pub let blacken tree = match tree with - | Node Red bulk left value right => Node Black bulk left value right + | Node {color=Red,size=bulk,left,value,right} => + construct Black bulk left value right | _ => tree end pub let rec blackHeight tree acc = match tree with | Leaf => acc - | Node Red _ left _ _ => blackHeight left acc - | Node Black _ left _ _ => blackHeight left (1 + acc) + | Node {color=Red,left} => blackHeight left acc + | Node {color=Black,left} => blackHeight left (1 + acc) end pub let rec searchHeight leftward target tree zipper = match tree with | Leaf => (Leaf, zipper) - | Node Red _ left value right => + | Node {color=Red,left,value,right} => if leftward then searchHeight leftward target left (Left Red value right :: zipper) else - searchHeight leftward target right (Right Red value left :: zipper) - | Node Black _ left value right => + searchHeight leftward target right (Right Red left value :: zipper) + | Node {color=Black,left,value,right} => if 0 == target then (tree,zipper) else if leftward then searchHeight leftward (target - 1) left (Left Black value right :: zipper) else - searchHeight leftward (target - 1) right (Right Black value left :: zipper) + searchHeight leftward (target - 1) right (Right Black left value :: zipper) end -pub let join_val value left right = +pub let joinVal left value right = let left = blacken left in let right = blacken right in let lbh = blackHeight left 0 in let rbh = blackHeight right 0 in if lbh == rbh then - makeNode Black left value right + makeNode Black left value right else if lbh > rbh then - (let (_left, zipper) = searchHeight False (lbh-rbh) left [] in - zipRed value _left right zipper) + (let (_left, zipper) = searchHeight False (lbh-rbh) left [] in + zipRed value _left right zipper) else - (let (_right, zipper) = searchHeight True (rbh-lbh) right [] in - zipRed value left _right zipper) + (let (_right, zipper) = searchHeight True (rbh-lbh) right [] in + zipRed value left _right zipper) pub let join left right = match left with | Leaf => right - | _ => match right with + | _ => + match right with | Leaf => left - | _ => match searchMax left [] with - | Right color value leftSmall :: zipper - => join_val value (deleteNearLeaf color leftSmall zipper) right + | _ => + match searchMax left [] with + | Right color leftSmall value :: zipper => + joinVal (deleteNearLeaf color leftSmall zipper) value right |_ => left end end end -pub let rec split func tree = +pub let rec split compareWithPivot tree = match tree with | Leaf => (None,Leaf,Leaf) - | Node _ _ left value right => match func value with + | Node {left,value,right} => + match compareWithPivot value with | Equal => (Some value, left, right) - | Less => let (_v, _l, _r) = split func left in - (_v, _l, join_val value _r right) - | Greater => let (_v, _l, _r) = split func right in - (_v, join_val value left _l, _r) + | Less => + let (_v, _l, _r) = split compareWithPivot left in + (_v, _l, joinVal _r value right) + | Greater => let (_v, _l, _r) = split compareWithPivot right in + (_v, joinVal left value _l, _r) end end diff --git a/lib/Set.fram b/lib/Set.fram new file mode 100644 index 00000000..632f0f44 --- /dev/null +++ b/lib/Set.fram @@ -0,0 +1,309 @@ +(* This file is part of DBL, released under MIT license. + * See LICENSE for details. +*) + +import open RedBlackTree + +(** Signature of Set *) + +pub data Set Elem = Set of { + T + , empty : T + , method isEmpty : T -> [] Bool + , method insert : T -> Elem -> [] T + , method remove : T -> Elem -> [] T + , method member : T -> Elem -> [] Bool + , method foldl : {type A,E} -> T -> (Elem -> A -> [|E] A) -> A -> [|E] A + , method foldr : {type A,E} -> T -> (Elem -> A -> [|E] A) -> A -> [|E] A + , method toList : T -> [] List Elem + , method union : T -> T -> [] T + , method intersection : T -> T -> [] T + , method diffrence : T -> T -> [] T + , method eq : T -> T -> [] Bool + , method subset : T -> T -> [] Bool + , method partionLt : T -> Elem -> [] (Pair T T) + , method partionGt : T -> Elem -> [] (Pair T T) + , method range : T -> Interval Elem -> Interval Elem -> [] T + , method least : T -> [] Option Elem + , method greatest : T -> [] Option Elem + , method leastGt : T -> Elem -> [] Option Elem + , method leastGeq : T -> Elem -> [] Option Elem + , method greatestLt : T -> Elem -> [] Option Elem + , method greatestLeq : T -> Elem -> [] Option Elem +} + +(** Red black tree implementation *) + +data rec Q Val = Nil | E of Val , Q Val | T of Tree Val , Q Val + +let rec eqMain eq qs1 qs2 = + match (qs1,qs2) with + | (Nil,Nil) => True + | (Nil, E _ _) => False + | (E _ _, Nil) => False + | (T Leaf rest, _) => eqMain eq rest qs2 + | (_, T Leaf rest) => eqMain eq qs1 rest + | (T (Node {left, value = elem, right}) rest, _) => + eqMain eq (T left (E elem (T right rest))) qs2 + | (_, T (Node {left, value = elem, right}) rest) => + eqMain eq qs1 (T left (E elem (T right rest))) + | (E elem1 rest1, E elem2 rest2) => + match eq elem1 elem2 with + | Noteq => False + | Eq => eqMain eq rest1 rest2 + end + end + +let rec subsetMain comp qs1 qs2 = + match (qs1,qs2) with + | (Nil,_) => True + | (E _ _ , Nil) => False + | (T Leaf rest, _) => subsetMain comp rest qs2 + | (_ , T Leaf rest) => subsetMain comp qs1 rest + | (T (Node {left, value = elem, right}) rest, _) => + subsetMain comp (T left (E elem (T right rest))) qs2 + | (_, T (Node {left, value = elem, right}) rest) => + subsetMain comp qs1 (T left (E elem (T right rest))) + | (E elem1 rest1, E elem2 rest2) => + match comp elem1 elem2 with + | Less => False + | Equal => subsetMain comp rest1 rest2 + | Greater => subsetMain comp qs1 rest2 + end + end + +let partionLt compare = fn tree key1 => let (_,left,right) = + split (fn key2 => match compare key1 key2 with + | Greater => Greater | _ => Less end) tree in (left,right) + +let partionGt compare = fn tree key1 => let (_, left,right) = + split (fn key2 => match compare key1 key2 with + | Less => Less | _ => Greater end) tree in (left,right) + +let rec least tree = + match tree with + | Leaf => None + | Node {left = Leaf, value = x} => Some x + | Node {left} => least left + end + +let rec greatest tree = + match tree with + | Leaf => None + | Node {value = x, right = Leaf} => Some x + | Node {right} => greatest right + end + +let empty = Leaf + +let isEmpty tree = + match tree with + | Leaf => True + | _ => False + end + +let rec member compare tree elem = + match tree with + | Leaf => False + | Node {left, value, right} => + match compare elem value with + | Less => member compare left elem + | Greater => member compare right elem + | Equal => True + end + end + +let insert compare tree elem = + match search (fn val => compare elem val) tree [] with + | (Leaf,zipper) => zipRed elem Leaf Leaf zipper + | (Node ,_) => tree + end + +let remove compare tree elem = + match search (fn val => compare elem val) tree [] with + | (Leaf,_) => tree + | (Node {color, left, right},zipper) => delete color left right zipper + end + +let rec _search compare tree elem = + match tree with + | Leaf => False + | Node {left, value, right} => + match compare elem value with + | Less => _search compare left elem + | Greater => _search compare right elem + | Equal => True + end + end + +let rec setFoldl tree func acc = + match tree with + | Leaf => acc + | Node {left, value, right} => + setFoldl right func (func value (setFoldl left func acc)) + end + +let rec setFoldr tree func acc = + match tree with + | Leaf => acc + | Node {left, value, right} => + setFoldr left func (func value (setFoldr right func acc)) + end + +let rec toList tree acc = + match tree with + | Leaf => acc + | Node {left, value, right} => + toList left (value :: toList right acc) + end + +let rec union compare tree1 tree2 = + match tree1 with + | Leaf => tree2 + | Node {left = left1, value = key1, right = right1} => + match tree2 with + | Leaf => tree1 + | Node => + let (_,left2,right2) = split (fn key2 => + compare key1 key2) tree2 in joinVal (union compare left1 left2) + key1 (union compare right1 right2) + end + end + +let rec intersection compare tree1 tree2 = + match tree1 with + | Leaf => Leaf + | Node {left = left1, value = key1, right = right1} => + match tree2 with + | Leaf => Leaf + | _ => let (value_out, left2, right2) = + split (fn key2 => compare key1 key2) tree2 + in let left = intersection compare left1 left2 + in let right = intersection compare right1 right2 + in match value_out with + | Some _ => joinVal left key1 right + | None => join left right + end + end + end + +let rec diffrence compare tree1 tree2 = + match tree1 with + | Leaf => Leaf + | Node {left = left1, value = key1, right = right1} => + match tree2 with + | Leaf => tree1 + | _ => + let (value_out, left2, right2) = + split (fn key2 => compare key1 key2) tree2 + in let left = diffrence compare left1 left2 + in let right = diffrence compare right1 right2 + in match value_out with + | Some _ => join left right + | None => joinVal left key1 right + end + end + end + +let subset compare set1 set2 = subsetMain compare (T set1 Nil) (T set2 Nil) + +let range compare tree left right = + match (left,right) with + | (Inclusion left, Inclusion right) => + let (_, tree') = partionLt compare tree left in + let (tree'',_) = partionGt compare tree' right in tree'' + | (Exclusion left, Inclusion right) => + let (_, tree') = partionGt compare tree left in + let (tree'',_) = partionGt compare tree' right in tree'' + | (Inclusion left, Exclusion right) => + let (_, tree') = partionLt compare tree left in + let (tree'',_) = partionLt compare tree' right in tree'' + | (Exclusion left, Exclusion right) => + let (_, tree') = partionGt compare tree left in + let (tree'',_) = partionLt compare tree' right in tree'' + end + +let rec leastGt compare tree val = + match tree with + | Leaf => None + | Node {left, value = key, right} => + match compare val key with + | Less => let x = leastGt compare left val in + match x with + | None => Some key + | _ => x + end + | Equal => least right + | Greater => leastGt compare right val + end + end + +let rec leastGeq compare tree val = + match tree with + | Leaf => None + | Node {left, value = key, right} => + match compare val key with + | Less => match leastGeq compare left val with + | None => Some key + | x => x + end + | Equal => Some val + | Greater => leastGeq compare right val + end + end + +let rec greatestLt compare tree val = + match tree with + | Leaf => None + | Node {left, value = key, right} => + match compare val key with + | Less => greatestLt compare left val + | Equal => greatest left + | Greater => match greatestLt compare right val with + | None => Some key + | x => x + end + end + end + +let rec greatestLeq compare tree val = + match tree with + | Leaf => None + | Node {left, value = key, right} => + match compare val key with + | Less => greatestLeq compare left val + | Equal => Some val + | Greater => match greatestLeq compare right val with + | None => Some key + | x => x + end + end + end + + +pub let make {Val} (compare : Val -> Val -> [] Ordered) = Set { + T = Tree Val + , empty = empty + , method isEmpty = isEmpty + , method insert = insert compare + , method remove = remove compare + , method member = member compare + , method foldl = setFoldl + , method foldr = setFoldr + , method toList = fn tree => toList tree [] + , method union = union compare + , method intersection = intersection compare + , method diffrence = diffrence compare + , method eq = fn set1 set2 => + eqMain (fn e1 e2 => (compare e1 e2).toComparable) (T set1 Nil) (T set2 Nil) + , method subset = subset compare + , method partionLt = partionLt compare + , method partionGt = partionGt compare + , method range = range compare + , method least = least + , method greatest = greatest + , method leastGt = leastGt compare + , method leastGeq = leastGeq compare + , method greatestLt = greatestLt compare + , method greatestLeq = greatestLeq compare +} diff --git a/test/stdlib/stdlib0001_Map.fram b/test/stdlib/stdlib0001_Map.fram index af01ffac..6f56375f 100644 --- a/test/stdlib/stdlib0001_Map.fram +++ b/test/stdlib/stdlib0001_Map.fram @@ -1,4 +1,4 @@ -import OrderedMap +import Map import open List import open Ordered import open Prelude @@ -11,7 +11,7 @@ let lt (v1 : Int) (v2 : Int) = else if v2 < v1 then Greater else Equal -let OrderedMap.Map {module IntMap} = OrderedMap.makeOrderedMap lt +let Map.Map {module IntMap} = Map.make lt let x = IntMap.empty @@ -24,10 +24,6 @@ let _ = assert (y.isEmpty == False) let _ = assert (z.isEmpty == False) let _ = assert (y.remove 1 >. isEmpty) -(* singleton check *) -let y = IntMap.singleton 1 1 -let _ = assert (y.toValueList == [1]) - (* domain check *) let z = y.insert 2 1 >. insert 3 2 >. insert 4 3 let _ = assert (z.domain == [1,2,3,4] && z.toValueList == [1,1,2,3]) @@ -78,15 +74,9 @@ let _ = assert (fst q >. toValueList == [3,2]) let _ = assert (snd q >. toValueList == [1,10,1,2,3]) (* rangeee check *) -let q = w.rangeee 0 2 +let q = w.range (Exclusion 0) (Exclusion 2) let _ = assert (q.toValueList == [10]) - -(* rangeii check *) -let q = w.rangeii 0 2 +let q = w.range (Inclusion 0) (Inclusion 2) let _ = assert (q.toValueList == [1,10,1]) - -(* rangeie check *) -let _ = assert (w.rangeie 0 2 >. toValueList == [1,10]) - -(* rangeei check *) -let _ = assert (w.rangeei 0 2 >. toValueList == [10,1]) +let _ = assert (w.range (Inclusion 0) (Exclusion 2) >. toValueList == [1,10]) +let _ = assert (w.range (Exclusion 0) (Inclusion 2) >. toValueList == [10,1]) diff --git a/test/stdlib/stdlib0002_Set.fram b/test/stdlib/stdlib0002_Set.fram index 0ad5cc5a..f64fd038 100644 --- a/test/stdlib/stdlib0002_Set.fram +++ b/test/stdlib/stdlib0002_Set.fram @@ -1,4 +1,4 @@ -import OrderedSet +import Set import open List import open Ordered import open Prelude @@ -11,15 +11,17 @@ let lt (v1 : Int) (v2 : Int) = else if v2 < v1 then Greater else Equal -let OrderedSet.Set {module IntSet} = OrderedSet.makeOrderedSet lt +let Set.Set {module IntSet} = Set.make lt (* empty check *) let x = IntSet.empty let _ = assert (x.isEmpty) -(* singletonSet check *) -let x = 0.singletonSet -let _ = assert (not x.isEmpty) +(* singletonSet check depricated *) +(*let x = 0.singletonSet +let _ = assert (not x.isEmpty)*) + +let x = x.insert 0 (* toList check *) let _ = assert (x.toList == [0]) @@ -65,11 +67,11 @@ let _ = assert (not (x.subset y)) let _ = assert (fst (y.partionLt 2) >. toList == [0,1]) let _ = assert (snd (y.partionLt 2) >. toList == [2,3]) -(* rangeii check *) -let _ = assert (y.rangeii 1 2 >. toList == [1,2]) +(* range check *) +let _ = assert (y.range (Inclusion 1) (Inclusion 2) >. toList == [1,2]) (* least check *) let _ = assert (match y.least with | Some x => x == 0 | _ => False end) (* greatest check *) -let _ = assert (match y.greatest with | Some x => x == 3 | _ => False end) \ No newline at end of file +let _ = assert (match y.greatest with | Some x => x == 3 | _ => False end) From 7bb419df44da187d5290c78d4ac160f979cf696e Mon Sep 17 00:00:00 2001 From: Jakub Chomiczewski Date: Fri, 29 Nov 2024 00:36:43 +0100 Subject: [PATCH 12/27] Correcting a lot of things mainly coding style --- lib/Map.fram | 465 +++++++++++++++++++++++++----------------- lib/Queue.fram | 132 ++++++------ lib/RedBlackTree.fram | 288 +++++++++++++------------- lib/Set.fram | 344 +++++++++++++++++-------------- 4 files changed, 674 insertions(+), 555 deletions(-) diff --git a/lib/Map.fram b/lib/Map.fram index 256190d2..c40f7177 100644 --- a/lib/Map.fram +++ b/lib/Map.fram @@ -7,167 +7,172 @@ import open RedBlackTree (** Signature *) pub data Map Key = Map of { - T - , empty : {type Val} -> Tree (T Val) - , method isEmpty : {type Val} -> Tree (T Val) -> [] Bool - , method insert : {type Val} -> Tree (T Val) -> - Key -> Val -> [] Tree (T Val) - , method insert' : {type Val} -> Tree (T Val) -> - Key -> Val -> [] (Pair (Tree (T Val)) Bool) - , method remove : {type Val} -> Tree (T Val) -> - Key -> [] Tree (T Val) - , method remove' : {type Val} -> Tree (T Val) -> - Key -> [] (Pair (Tree (T Val)) Bool) - , method member : {type Val} -> Tree (T Val) -> Key -> [] Bool - , method find : {type Val} -> Tree (T Val) -> Key -> [] Option Val - , method operate : {type Val,E} -> Tree (T Val) -> Key -> + T + , empty : {type Val} -> T Val + , method isEmpty : {type Val} -> T Val -> [] Bool + , method insert : {type Val} -> T Val -> + Key -> Val -> [] T Val + , method insertChange : {type Val} -> T Val -> + Key -> Val -> [] (Pair (T Val) Bool) + , method remove : {type Val} -> T Val -> + Key -> [] T Val + , method removeChange : {type Val} -> T Val -> + Key -> [] (Pair (T Val) Bool) + , method member : {type Val} -> T Val -> Key -> [] Bool + , method find : {type Val} -> T Val -> Key -> [] Option Val + (** @brief method that searches for an item and returns value + based on the search + @param key + @param absentf what value return if the element doesn't exist + @param presentf what value return if the element exist + @return tuple of found an item and it's value, + result of a given function absentf or presentf and orginal tree + *) + , method operate : {type Val,E} -> T Val -> Key -> (Unit -> [|E] Option Val) -> (Val -> [|E] Option Val) -> - [|E] (Pair (Pair (Option Val) (Option Val)) (Tree (T Val))) - , method foldl : {type Val, type A,E} -> Tree (T Val) -> + [|E] (Pair (Pair (Option Val) (Option Val)) (T Val)) + , method foldl : {type Val, type A,E} -> T Val -> (Key -> Val -> A -> [|E] A) -> A -> [|E] A - , method foldr : {type Val, type A,E} -> Tree (T Val) -> + , method foldr : {type Val, type A,E} -> T Val -> (Key -> Val -> A -> [|E] A) -> A -> [|E] A - , method toList : {type Val} -> Tree (T Val) -> [] List (Pair Key Val) - , method toValueList : {type Val} -> Tree (T Val) -> [] List Val - , method domain : {type Val} -> Tree (T Val) -> [] List Key - , method map : {type Val, type A,E} -> Tree (T Val) -> - (Val -> [|E] A) -> [|E] Tree (T A) - , method map2 : {type Val, type A,E} -> Tree (T Val) -> - (Key -> [|E] A) -> [|E] Tree (T A) - , method app : {type Val,E} -> Tree (T Val) -> + , method toList : {type Val} -> T Val -> [] List (Pair Key Val) + , method toValueList : {type Val} -> T Val -> [] List Val + , method domain : {type Val} -> T Val -> [] List Key + , method mapVal : {type Val, type A,E} -> T Val -> + (Val -> [|E] A) -> [|E] T A + , method mapKey : {type Val, type A,E} -> T Val -> + (Key -> [|E] A) -> [|E] T A + , method app : {type Val,E} -> T Val -> (Key -> Val -> [|E] Unit) -> [|E] Unit - , method union : {type Val,E} -> Tree (T Val) -> Tree (T Val) -> - (Key -> Val -> Val -> [|E] Val) -> [|E] Tree (T Val) - , method partion : {type Val} -> Tree (T Val) -> Key -> - [] (Pair (Pair (Tree (T Val)) (Option Val)) (Tree (T Val))) - , method partionLt : {type Val} -> Tree (T Val) -> Key -> - [] Pair (Tree (T Val)) (Tree (T Val)) - , method partionGt : {type Val} -> Tree (T Val) -> Key -> - [] Pair (Tree (T Val)) (Tree (T Val)) - , method range : {type Val} -> Tree (T Val) -> Interval Key -> - Interval Key -> [] Tree (T Val) - , method least : {type Val} -> Tree (T Val) -> [] Option (T Val) - , method greatest : {type Val} -> Tree (T Val) -> [] Option (T Val) - , method leastGt : {type Val} -> Tree (T Val) -> Key -> [] Option (T Val) - , method leastGeq : {type Val} -> Tree (T Val) -> Key -> [] Option (T Val) - , method greatestLt : {type Val} -> Tree (T Val) -> - Key -> [] Option (T Val) - , method greatestLeq : {type Val,E} -> Tree (T Val) -> - Key -> [] Option (T Val) + , method union : {type Val,E} -> T Val -> T Val -> + (Key -> Val -> Val -> [|E] Val) -> [|E] T Val + , method partion : {type Val} -> T Val -> Key -> + [] (Pair (Pair (T Val) (Option Val)) (T Val)) + , method partionLt : {type Val} -> T Val -> Key -> + [] Pair (T Val) (T Val) + , method partionGt : {type Val} -> T Val -> Key -> + [] Pair (T Val) (T Val) + , method range : {type Val} -> T Val -> Interval Key -> + Interval Key -> [] T Val + , method least : {type Val} -> T Val -> [] Option (Pair Key Val) + , method greatest : {type Val} -> T Val -> [] Option (Pair Key Val) + , method leastGt : {type Val} -> T Val -> Key -> [] Option (Pair Key Val) + , method leastGeq : {type Val} -> T Val -> Key -> [] Option (Pair Key Val) + , method greatestLt : {type Val} -> T Val -> + Key -> [] Option (Pair Key Val) + , method greatestLeq : {type Val,E} -> T Val -> + Key -> [] Option (Pair Key Val) } (** implementation *) let isEmpty tree = match tree with - | Leaf => True - | _ => False + | Leaf => True + | _ => False end -let insert compare tree key val = +let insert compare tree key val = match search (fn (key', _ ) => compare key key') tree [] with - | (Leaf, zipper) => zipRed (key,val) Leaf Leaf zipper - | ((Node {color, size = bulk, left, right}), zipper) => - zip (construct color bulk left (key,val) right) zipper + | (Leaf, zipper) => zipRed (key,val) Leaf Leaf zipper + | ((Node {color, size = bulk, left, right}), zipper) => + zip (construct color bulk left (key,val) right) zipper end let insert' compare tree key val = match search (fn (key', _ ) => compare key key') tree [] with - | (Leaf, zipper) => (zipRed (key,val) Leaf Leaf zipper, False) - | ((Node {color, size = bulk, left, right}), zipper) => - (zip (construct color bulk left (key,val) right) zipper, True) + | (Leaf, zipper) => (zipRed (key,val) Leaf Leaf zipper, False) + | ((Node {color, size = bulk, left, right}), zipper) => + (zip (construct color bulk left (key,val) right) zipper, True) end let remove compare tree key = match search (fn (key', _ ) => compare key key') tree [] with - | (Leaf,_) => tree - | (Node {color, left, right}, zipper) => - delete color left right zipper + | (Leaf,_) => tree + | (Node {color, left, right}, zipper) => + delete color left right zipper end let remove' compare tree key = match search (fn (key', _ ) => compare key key') tree [] with - | (Leaf,_) => (tree,False) - | (Node {color, left, right}, zipper) => - (delete color left right zipper, True) + | (Leaf,_) => (tree,False) + | (Node {color, left, right}, zipper) => + (delete color left right zipper, True) end let rec member compare tree key = match tree with - | Leaf => False - | Node {left, value = (key',_), right} => - match compare key key' with - | Less => member compare left key - | Equal => True - | Greater => member compare right key - end + | Leaf => False + | Node {left, value = (key',_), right} => + match compare key key' with + | Less => member compare left key + | Equal => True + | Greater => member compare right key + end end let rec find compare tree key = match tree with - | Leaf => None - | Node {left, value = (key', val), right} => - match compare key key' with - | Less => find compare left key - | Equal => Some val - | Greater => find compare right key - end + | Leaf => None + | Node {left, value = (key', val), right} => + match compare key key' with + | Less => find compare left key + | Equal => Some val + | Greater => find compare right key + end end let rec operate compare tree key absentf presentf = match search (fn (key', _ ) => compare key key') tree [] with | (Leaf, zipper) => match absentf () with - | None => (None,None, tree) - | Some x => (None,Some x, zipRed (key,x) Leaf Leaf zipper) + | None => (None,None, tree) + | Some x => (None,Some x, zipRed (key,x) Leaf Leaf zipper) end | (Node {color, size = bulk, left, value = (_, val), right}, zipper) => match presentf val with - | None => (Some val, None, delete color left right zipper) - | Some x => (Some val, Some x, zip - (construct color bulk left (key,x) right) zipper) + | None => (Some val, None, delete color left right zipper) + | Some x => (Some val, Some x, zip + (construct color bulk left (key,x) right) zipper) end end let rec foldr func tree acc = match tree with - | Leaf => acc - | Node {left, value = (key, val), right} => - let val_right = (foldr func right acc) in - let val_middle = (func key val val_right) in - foldr func left val_middle + | Leaf => acc + | Node {left, value = (key, val), right} => + let val_right = (foldr func right acc) in + let val_middle = (func key val val_right) in + foldr func left val_middle end -let mapFoldr tree func acc = foldr func tree acc - let rec foldl func tree acc = match tree with - | Leaf => acc - | Node {left, value = (key, val), right} => - let val_left = (foldl func left acc) in - let val_middle = (func key val val_left) in - foldl func right val_middle + | Leaf => acc + | Node {left, value = (key, val), right} => + let val_left = (foldl func left acc) in + let val_middle = (func key val val_left) + in foldl func right val_middle end -let mapFoldl tree func acc = foldl func tree acc - -let rec map tree func = match tree with - | Leaf => Leaf - | Node {color, size = bulk, left, value = (key,value), right} => - construct color bulk (map left func) (key,func value) (map right func) +let rec map tree func = + match tree with + | Leaf => Leaf + | Node {color, size, left, value = (key,value), right} => + construct color size (map left func) (key,func value) (map right func) end -let rec map2 tree func = match tree with - | Leaf => Leaf - | Node {color, size = bulk, left, value = (key, _), right} => - construct color bulk (map2 left func) (key, func key) (map2 right func) +let rec map2 tree func = + match tree with + | Leaf => Leaf + | Node {color, size = bulk, left, value = (key, _), right} => + construct color bulk (map2 left func) (key, func key) (map2 right func) end -let rec app tree func = match tree with - | Leaf => () - | Node {left, value = (key,value), right} => - let _ = app left func in - let _ = func key value in - app right func +let rec app tree func = + match tree with + | Leaf => () + | Node {left, value = (key,value), right} => + app left func; func key value; app right func end let rec union compare tree1 tree2 merge = @@ -176,98 +181,111 @@ let rec union compare tree1 tree2 merge = | Node {left = left1, value = (key1,value1), right = right1} => match tree2 with | Leaf => tree1 - | _ => let (output,left2,right2) = + | _ => + let (output,left2,right2) = split (fn (key2,_) => compare key1 key2) tree2 - in let new_pair = match output with - | None => (key1,value1) - | Some (_,value2) => (key1, merge key1 value1 value2) - end in joinVal (union compare left1 left2 merge) new_pair - (union compare right1 right2 merge) + in + let new_pair = + match output with + | None => (key1,value1) + | Some (_,value2) => (key1, merge key1 value1 value2) + end + in + joinVal (union compare left1 left2 merge) new_pair + (union compare right1 right2 merge) end end let partionLt compare tree key = let (_,left,right) = split (fn (key2,_) => match compare key key2 with - | Less => Less - | _ => Greater - end) tree in (left, right) + | Less => Less + | _ => Greater + end) tree + in + (left, right) let partionGt compare tree key = let (_,left,right) = split (fn (key2,_) => - match compare key key2 with - | Greater => Greater - | _ => Less - end) tree in (left, right) + match compare key key2 with + | Greater => Greater + | _ => Less + end) tree + in + (left, right) let rec least tree = match tree with - | Leaf => None - | Node {left = Leaf, value} => Some value - | Node {left} => least left + | Leaf => None + | Node {left = Leaf, value} => Some value + | Node {left} => least left end let rec greatest tree = match tree with - | Leaf => None - | Node { value, right=Leaf} => Some value - | Node {right} => greatest right + | Leaf => None + | Node { value, right=Leaf} => Some value + | Node {right} => greatest right end let rec leastGt compare tree key = match tree with - | Leaf => None - | Node {left, value = (key1, value), right} => - match compare key key1 with - | Less => match leastGt compare left key with - | None => Some (key1, value) - | x => x - end - | Equal => least right - | Greater => leastGt compare right key + | Leaf => None + | Node {left, value = (key1, value), right} => + match compare key key1 with + | Less => + match leastGt compare left key with + | None => Some (key1, value) + | x => x + end + | Equal => least right + | Greater => leastGt compare right key end end let rec leastGeq compare tree key = match tree with - | Leaf => None - | Node {left, value = (key1, value), right} => - match compare key key1 with - | Less => match leastGeq compare left key with - | None => Some (key1,value) - | x => x - end - | Equal => Some (key1, value) - | Greater => leastGeq compare right key + | Leaf => None + | Node {left, value = (key1, value), right} => + match compare key key1 with + | Less => + match leastGeq compare left key with + | None => Some (key1,value) + | x => x + end + | Equal => Some (key1, value) + | Greater => leastGeq compare right key end end let rec greatestLt compare tree key = match tree with - | Leaf => None - | Node {left, value = (key1,value), right} => - match compare key key1 with - | Less => greatestLt compare left key - | Equal => greatest left - | Greater => match greatestLt compare right key with - | None => Some (key1,value) - | x => x + | Leaf => None + | Node {left, value = (key1,value), right} => + match compare key key1 with + | Less => greatestLt compare left key + | Equal => greatest left + | Greater => + match greatestLt compare right key with + | None => Some (key1,value) + | x => x + end end - end end let rec greatestLeq compare tree key = match tree with - | Leaf => None - | Node {left, value = (key1,value), right} => - match compare key key1 with - | Less => greatestLt compare left key - | Equal => Some (key1,value) - | Greater => match greatestLeq compare right key with - | None => Some (key1,value) - | x => x + | Leaf => None + | Node {left, value = (key1,value), right} => + match compare key key1 with + | Less => greatestLt compare left key + | Equal => Some (key1,value) + | Greater => + match greatestLeq compare right key with + | None => Some (key1,value) + | x => x + end end - end end let toList tree = foldr (fn key value acc => (key, value) :: acc) tree [] @@ -278,10 +296,11 @@ let domain tree = foldr (fn key value acc => key :: acc) tree [] let partion compare tree key = let (output,left,right) = split (fn (key2,_) => compare key key2) tree - in match output with - | None => (left,None,right) - | Some (_,x) => (left,Some x, right) - end + in + match output with + | None => (left,None,right) + | Some (_,x) => (left,Some x, right) + end let range compare tree left right = match (left,right) with @@ -299,37 +318,103 @@ let range compare tree left right = let (result,_) = partionGt compare middle right in result end +data MapT Key Val = MapT of Tree (Pair Key Val) + +// Wrappers +let isEmptyT (MapT tree) = isEmpty tree + +let insertT compare (MapT tree) key val = MapT (insert compare tree key val) + +let insertChangeT compare (MapT tree) key val = + let (tree,bool) = insert' compare tree key val in (MapT tree, bool) + +let removeT compare (MapT tree) key = MapT (remove compare tree key) + +let removeChangeT compare (MapT tree) key = + let (tree,bool) = remove' compare tree key in (MapT tree, bool) + +let memberT compare (MapT tree) key = member compare tree key + +let findT compare (MapT tree) key = find compare tree key + +let operateT compare (MapT tree) key absentf presentf = + let (val,res,tree) = operate compare tree key absentf presentf + in (val,res, MapT tree) + +let mapFoldl (MapT tree) func acc = foldl func tree acc + +let mapFoldr (MapT tree) func acc = foldr func tree acc + +let toListT (MapT tree) = toList tree + +let toValueListT (MapT tree) = toValueList tree + +let domainT (MapT tree) = domain tree + +let mapVal (MapT tree) func = MapT (map tree func) + +let mapKey (MapT tree) func = MapT (map2 tree func) + +let appT (MapT tree) func = app tree func + +let unionT compare (MapT tree1) (MapT tree2) merge = + MapT (union compare tree1 tree2 merge) + +let partionT compare (MapT tree) key = + let (t1,v,t2) = partion compare tree key + in (MapT t1, v, MapT t2) + +let partionLtT compare (MapT tree) key = + let (t1,t2) = partionLt compare tree key + in (MapT t1, MapT t2) + +let partionGtT compare (MapT tree) key = + let (t1,t2) = partionGt compare tree key + in (MapT t1, MapT t2) + +let rangeT compare (MapT tree) left right = + MapT (range compare tree left right) + +let leastT (MapT tree) = least tree + +let greatest (MapT tree) = greatest tree + +let leastGtT compare (MapT tree) key = leastGt compare tree key + +let greatestLtT compare (MapT tree) key = greatestLt compare tree key +let leastGeqT compare (MapT tree) key = leastGeq compare tree key +let greatestLeqT compare (MapT tree) key = greatestLeq compare tree key pub let make {Key} (compare : Key -> Key -> [] Ordered) = Map { - T = Pair Key - , empty = Leaf - , method isEmpty = isEmpty - , method insert = insert compare - , method insert' = insert' compare - , method remove = remove compare - , method remove' = remove' compare - , method member = member compare - , method find = find compare - , method operate = operate compare + T = MapT Key + , empty = MapT Leaf + , method isEmpty = isEmptyT + , method insert = insertT compare + , method insertChange = insertChangeT compare + , method remove = removeT compare + , method removeChange = removeChangeT compare + , method member = memberT compare + , method find = findT compare + , method operate = operateT compare , method foldl = mapFoldl , method foldr = mapFoldr - , method toList = toList - , method toValueList = toValueList - , method domain = domain - , method map = map - , method map2 = map2 - , method app = app - , method union = union compare - , method partion = partion compare - , method partionLt = partionLt compare - , method partionGt = partionGt compare - , method range = range compare - , method least = least + , method toList = toListT + , method toValueList = toValueListT + , method domain = domainT + , method mapVal = mapVal + , method mapKey = mapKey + , method app = appT + , method union = unionT compare + , method partion = partionT compare + , method partionLt = partionLtT compare + , method partionGt = partionGtT compare + , method range = rangeT compare + , method least = leastT , method greatest = greatest - , method leastGt = leastGt compare - , method leastGeq = leastGeq compare - , method greatestLt = greatestLt compare - , method greatestLeq = greatestLeq compare + , method leastGt = leastGtT compare + , method leastGeq = leastGeqT compare + , method greatestLt = greatestLtT compare + , method greatestLeq = greatestLeqT compare } diff --git a/lib/Queue.fram b/lib/Queue.fram index acc43eb5..86f87913 100644 --- a/lib/Queue.fram +++ b/lib/Queue.fram @@ -5,16 +5,16 @@ data NotNegativeInt = Zero | Positive of Int let addOne value = -match value with -| Zero => Positive 1 -| Positive n => Positive (n+1) -end + match value with + | Zero => Positive 1 + | Positive n => Positive (n+1) + end let subOne value = -match value with -| Zero => Zero -| Positive n => if n == 1 then Zero else Positive (n-1) -end + match value with + | Zero => Zero + | Positive n => if n == 1 then Zero else Positive (n-1) + end data RotationState Val = | Idle @@ -27,84 +27,84 @@ data HoodMelvilleQueue Val = NotNegativeInt, List Val let exec state = -match state with - | Reversing ok (x::f) f' (y::r) r' => - Reversing (addOne ok) f (x::f') r (y::r') - | Reversing ok [] f' [y] r' => Appending ok f' (y::r') - | Appending Zero f' r' => Done r' - | Appending ok (x::f') r' => Appending (subOne ok) f' (x::r') - | _ => state -end + match state with + | Reversing ok (x::f) f' (y::r) r' => + Reversing (addOne ok) f (x::f') r (y::r') + | Reversing ok [] f' [y] r' => Appending ok f' (y::r') + | Appending Zero f' r' => Done r' + | Appending ok (x::f') r' => Appending (subOne ok) f' (x::r') + | _ => state + end let invalidate state = -match state with - | Reversing ok f f' r r' => Reversing (subOne ok) f f' r r' - | Appending Zero f' (x::r') => Done r' - | Appending ok f' r' => Appending (subOne ok) f' r' - | _ => state -end + match state with + | Reversing ok f f' r r' => Reversing (subOne ok) f f' r r' + | Appending Zero f' (x::r') => Done r' + | Appending ok f' r' => Appending (subOne ok) f' r' + | _ => state + end let exec_twice hmqueue = -match hmqueue with -| HMQueue lenf f state lenr r => - match exec (exec state) with - | Done newf => HMQueue lenf newf Idle lenr r - | newstate => HMQueue lenf f newstate lenr r + match hmqueue with + | HMQueue lenf f state lenr r => + match exec (exec state) with + | Done newf => HMQueue lenf newf Idle lenr r + | newstate => HMQueue lenf f newstate lenr r + end end -end let leq v1 v2 = -match (v1,v2) with -| (Zero,Zero) => True -| (Zero,Positive _) => True -| (Positive _, Zero) => False -| (Positive n, Positive m) => n <= m -end + match (v1,v2) with + | (Zero,Zero) => True + | (Zero,Positive _) => True + | (Positive _, Zero) => False + | (Positive n, Positive m) => n <= m + end let add v1 v2 = -match (v1,v2) with -| (Zero,any) => any -| (any,Zero) => any -| (Positive n, Positive m) => Positive (n+m) -end + match (v1,v2) with + | (Zero,any) => any + | (any,Zero) => any + | (Positive n, Positive m) => Positive (n+m) + end let check queue = -match queue with -| HMQueue lenf f state lenr r => -if leq lenr lenf then exec_twice queue -else ( - let newstate = Reversing Zero f [] r [] in - exec_twice (HMQueue (add lenf lenr) f newstate Zero []) -) -end + match queue with + | HMQueue lenf f state lenr r => + if leq lenr lenf then exec_twice queue + else ( + let newstate = Reversing Zero f [] r [] in + exec_twice (HMQueue (add lenf lenr) f newstate Zero []) + ) + end pub let emptyQueue = HMQueue Zero [] Idle Zero [] pub let isEmpty queue = -match queue with -| HMQueue Zero _ _ _ _ => True -| _ => False -end + match queue with + | HMQueue Zero _ _ _ _ => True + | _ => False + end let snoc queue value = -match queue with -| HMQueue lenf f state lenr r => -check (HMQueue lenf f state (addOne lenr) (value :: r)) -end + match queue with + | HMQueue lenf f state lenr r => + check (HMQueue lenf f state (addOne lenr) (value :: r)) + end let head queue = -match queue with -| HMQueue Zero _ _ _ _ => None -| HMQueue _ (x::xs) _ _ _ => Some x -| _ => None // Impossible -end + match queue with + | HMQueue Zero _ _ _ _ => None + | HMQueue _ (x::xs) _ _ _ => Some x + | _ => None // Impossible + end let tail queue = -match queue with -| HMQueue Zero _ _ _ _ => emptyQueue -| HMQueue _ [] _ _ _ => emptyQueue -| HMQueue lenf (x::xs) state lenr r => -check (HMQueue (subOne lenf) xs (invalidate state) lenr r) -end + match queue with + | HMQueue Zero _ _ _ _ => emptyQueue + | HMQueue _ [] _ _ _ => emptyQueue + | HMQueue lenf (x::xs) state lenr r => + check (HMQueue (subOne lenf) xs (invalidate state) lenr r) + end pub method isEmpty = isEmpty self diff --git a/lib/RedBlackTree.fram b/lib/RedBlackTree.fram index 83b0eb5c..baec3efb 100644 --- a/lib/RedBlackTree.fram +++ b/lib/RedBlackTree.fram @@ -10,11 +10,13 @@ data Color = | Black pub data rec Tree Value = | Leaf - | Node of {color: Color, - size: Int, - left: Tree Value, - value: Value, - right: Tree Value} + | Node of { + color: Color, + size: Int, + left: Tree Value, + value: Value, + right: Tree Value + } data ZipElem Value = | Left of Color, Value, Tree Value | Right of Color, Tree Value, Value @@ -22,168 +24,168 @@ data ZipElem Value = pub let empty = Leaf pub let size tree = - match tree with - | Leaf => 0 - | Node {size} => size - end + match tree with + | Leaf => 0 + | Node {size} => size + end pub let makeNode color left value right = - Node {color, size = size left + size right + 1, left, value, right} + Node {color, size = size left + size right + 1, left, value, right} pub let construct color size left value right = Node {color,size,left,value,right} pub let rec zip tree zipper = - match zipper with - | [] => tree + match zipper with + | [] => tree - | Left color value right :: rest => - zip (makeNode color tree value right) rest + | Left color value right :: rest => + zip (makeNode color tree value right) rest - | Right color left value :: rest => - zip (makeNode color left value tree) rest + | Right color left value :: rest => + zip (makeNode color left value tree) rest end pub let rec zipRed value left right zipper = - match zipper with - |[] => makeNode Black left value right - - |Left Black value1 right1 :: rest => - zip (makeNode Black (makeNode Red left value right) value1 right1) rest - - | Right Black left1 value1 :: rest => - zip (makeNode Black left1 value1 (makeNode Red left value right)) rest - - |Left Red value1 right1 :: - Left _ value2 - (Node {color = Red, size = bulk3, left = left3, - value = value3, right = right3}) :: rest => - zipRed value2 - (makeNode Black (makeNode Red left value right) value1 right1) - (construct Black bulk3 left3 value3 right3) rest - - |Left Red value1 right1 :: - Right _ - (Node {color = Red, size = bulk3, left = left3, + match zipper with + |[] => makeNode Black left value right + + |Left Black value1 right1 :: rest => + zip (makeNode Black (makeNode Red left value right) value1 right1) rest + + | Right Black left1 value1 :: rest => + zip (makeNode Black left1 value1 (makeNode Red left value right)) rest + + | Left Red value1 right1 :: + Left _ value2 + (Node {color = Red, size = bulk3, left = left3, + value = value3, right = right3}) :: rest => + zipRed value2 + (makeNode Black (makeNode Red left value right) value1 right1) + (construct Black bulk3 left3 value3 right3) rest + + | Left Red value1 right1 :: + Right _ + (Node {color = Red, size = bulk3, left = left3, + value = value3, right = right3}) value2 :: rest => + zipRed value2 + (construct Black bulk3 left3 value3 right3) + (makeNode Black (makeNode Red left value right) value1 right1) rest + + | Right Red left1 value1 :: + Left _ value2 + (Node {color = Red, size = bulk3, left = left3, + value = value3, right = right3}) :: rest => + zipRed value2 + (makeNode Black left1 value1 (makeNode Red left value right)) + (construct Black bulk3 left3 value3 right3) rest + + | Right Red left1 value1 :: + Right _ (Node {color = Red, size = bulk3, left = left3, value = value3, right = right3}) value2 :: rest => - zipRed value2 - (construct Black bulk3 left3 value3 right3) - (makeNode Black (makeNode Red left value right) value1 right1) rest - - |Right Red left1 value1 :: - Left _ value2 - (Node {color = Red, size = bulk3, left = left3, - value = value3, right = right3}) :: rest => - zipRed value2 - (makeNode Black left1 value1 (makeNode Red left value right)) - (construct Black bulk3 left3 value3 right3) rest - - |Right Red left1 value1 :: - Right _ (Node {color = Red, size = bulk3, left = left3, - value = value3, right = right3}) value2 :: rest => - zipRed value2 - (construct Black bulk3 left3 value3 right3) - (makeNode Black left1 value1 (makeNode Red left value right)) rest - - |Left Red value1 right1 :: - Left _ value2 node3 :: rest => - zip - (makeNode Black (makeNode Red left value right) value1 - (makeNode Red right1 value2 node3)) rest - - |Left Red value1 right1 :: - Right _ node3 value2 :: rest => - zip - (makeNode Black (makeNode Red node3 value2 left) - value (makeNode Red right value1 right1)) rest - - |Right Red left1 value1 :: - Left _ value2 node3 :: rest => - zip - (makeNode Black (makeNode Red left1 value1 left) - value (makeNode Red right value2 node3)) rest - - |Right Red left1 value1 :: - Right _ node3 value2 :: rest => - zip - (makeNode Black (makeNode Red node3 value2 left1) - value1 (makeNode Red left value right)) rest - - |Left Red value1 right1 :: + zipRed value2 + (construct Black bulk3 left3 value3 right3) + (makeNode Black left1 value1 (makeNode Red left value right)) rest + + | Left Red value1 right1 :: + Left _ value2 node3 :: rest => + zip + (makeNode Black (makeNode Red left value right) value1 + (makeNode Red right1 value2 node3)) rest + + | Left Red value1 right1 :: + Right _ node3 value2 :: rest => + zip + (makeNode Black (makeNode Red node3 value2 left) + value (makeNode Red right value1 right1)) rest + + | Right Red left1 value1 :: + Left _ value2 node3 :: rest => + zip + (makeNode Black (makeNode Red left1 value1 left) + value (makeNode Red right value2 node3)) rest + + | Right Red left1 value1 :: + Right _ node3 value2 :: rest => + zip + (makeNode Black (makeNode Red node3 value2 left1) + value1 (makeNode Red left value right)) rest + + | Left Red value1 right1 :: [] => makeNode Black (makeNode Red left value right) value1 right1 - |Right Red left1 value1 :: + | Right Red left1 value1 :: [] => makeNode Black left1 value1 (makeNode Red left value right) end pub let rec zipBlack tree zipper = - match zipper with - |[] => tree - - |Left color1 value1 - (Node {left = left2, value = value2, - right = (Node {color = Red, size = bulk3, - left = left3, value = value3, right = right3})}) :: - rest => - zip - (makeNode color1 (makeNode Black tree value1 left2 ) value2 - (construct Black bulk3 left3 value3 right3)) rest - - |Right color1 (Node { left = (Node {color = Red, size = bulk3, left = left3, - value = value3, right = right3}), value = value2, right = right2}) - value1 :: rest => - zip - (makeNode color1 (construct Black bulk3 left3 value3 right3) value2 - (makeNode Black right2 value1 tree)) rest - - |Left color1 value1 (Node {left = (Node {color = Red, left = left3, - value = value3, right = right3}), value = value2, right = right2}) :: rest => - zip - (makeNode color1 (makeNode Black tree value1 left3) value3 - (makeNode Black right3 value2 right2)) rest - - |Right color1 (Node {left = left2, value = value2, right = - (Node {color = Red,left = left3, value = value3, right = right3})}) - value1 :: rest => - zip (makeNode color1 (makeNode Black left2 value2 left3) - value3 (makeNode Black right3 value1 tree)) rest - - |Left Red value1 (Node {size = bulk2, left = left2, - value = value2, right=right2}) :: rest => - zip - (makeNode Black tree value1 (construct Red bulk2 left2 value2 right2)) rest - - |Right Red (Node {size = bulk2, left = left2, - value = value2, right = right2}) value1 :: rest => - zip - (makeNode Black (construct Red bulk2 left2 value2 right2) value1 tree) rest - - |Left Black value1 (Node {color = Black, size = bulk2, left = left2, - value = value2,right = right2}) :: rest => - zipBlack - (makeNode Black tree value1 (construct Red bulk2 left2 value2 right2)) rest - - |Right Black (Node {color = Black, size = bulk2, left = left2, - value = value2, right = right2}) value1 :: rest => - zipBlack - (makeNode Black (construct Red bulk2 left2 value2 right2) value1 tree) rest - - |Left Black value1 (Node {color = Red, left = left2, - value = value2, right = right2}) :: rest => - zipBlack - tree (Left Red value1 left2 :: Left Black value2 right2 :: rest) - - |Right Black (Node {color = Red, left = left2, value = value2, - right = right2}) value1 :: rest => - zipBlack - tree (Right Red right2 value1 :: Right Black left2 value2 :: rest) + match zipper with + | [] => tree + + | Left color1 value1 + (Node {left = left2, value = value2, + right = (Node {color = Red, size = bulk3, + left = left3, value = value3, right = right3})}) :: + rest => + zip + (makeNode color1 (makeNode Black tree value1 left2 ) value2 + (construct Black bulk3 left3 value3 right3)) rest + + | Right color1 (Node { left = (Node {color = Red, size = bulk3, left = left3, + value = value3, right = right3}), value = value2, right = right2}) + value1 :: rest => + zip + (makeNode color1 (construct Black bulk3 left3 value3 right3) value2 + (makeNode Black right2 value1 tree)) rest + + | Left color1 value1 (Node {left = (Node {color = Red, left = left3, + value = value3, right = right3}), value = value2, right = right2}) :: rest => + zip + (makeNode color1 (makeNode Black tree value1 left3) value3 + (makeNode Black right3 value2 right2)) rest + + | Right color1 (Node {left = left2, value = value2, right = + (Node {color = Red,left = left3, value = value3, right = right3})}) + value1 :: rest => + zip (makeNode color1 (makeNode Black left2 value2 left3) + value3 (makeNode Black right3 value1 tree)) rest + + | Left Red value1 (Node {size = bulk2, left = left2, + value = value2, right=right2}) :: rest => + zip + (makeNode Black tree value1 (construct Red bulk2 left2 value2 right2)) rest + + | Right Red (Node {size = bulk2, left = left2, + value = value2, right = right2}) value1 :: rest => + zip + (makeNode Black (construct Red bulk2 left2 value2 right2) value1 tree) rest + + | Left Black value1 (Node {color = Black, size = bulk2, left = left2, + value = value2,right = right2}) :: rest => + zipBlack + (makeNode Black tree value1 (construct Red bulk2 left2 value2 right2)) rest + + | Right Black (Node {color = Black, size = bulk2, left = left2, + value = value2, right = right2}) value1 :: rest => + zipBlack + (makeNode Black (construct Red bulk2 left2 value2 right2) value1 tree) rest + + | Left Black value1 (Node {color = Red, left = left2, + value = value2, right = right2}) :: rest => + zipBlack + tree (Left Red value1 left2 :: Left Black value2 right2 :: rest) + + | Right Black (Node {color = Red, left = left2, value = value2, + right = right2}) value1 :: rest => + zipBlack + tree (Right Red right2 value1 :: Right Black left2 value2 :: rest) //Impossible - | Left _ _ Leaf :: _ => tree + | Left _ _ Leaf :: _ => tree - | Right _ Leaf _ :: _ => tree + | Right _ Leaf _ :: _ => tree end diff --git a/lib/Set.fram b/lib/Set.fram index 632f0f44..89e423ed 100644 --- a/lib/Set.fram +++ b/lib/Set.fram @@ -7,29 +7,29 @@ import open RedBlackTree (** Signature of Set *) pub data Set Elem = Set of { - T - , empty : T - , method isEmpty : T -> [] Bool - , method insert : T -> Elem -> [] T - , method remove : T -> Elem -> [] T - , method member : T -> Elem -> [] Bool - , method foldl : {type A,E} -> T -> (Elem -> A -> [|E] A) -> A -> [|E] A - , method foldr : {type A,E} -> T -> (Elem -> A -> [|E] A) -> A -> [|E] A - , method toList : T -> [] List Elem - , method union : T -> T -> [] T - , method intersection : T -> T -> [] T - , method diffrence : T -> T -> [] T - , method eq : T -> T -> [] Bool - , method subset : T -> T -> [] Bool - , method partionLt : T -> Elem -> [] (Pair T T) - , method partionGt : T -> Elem -> [] (Pair T T) - , method range : T -> Interval Elem -> Interval Elem -> [] T - , method least : T -> [] Option Elem - , method greatest : T -> [] Option Elem - , method leastGt : T -> Elem -> [] Option Elem - , method leastGeq : T -> Elem -> [] Option Elem - , method greatestLt : T -> Elem -> [] Option Elem - , method greatestLeq : T -> Elem -> [] Option Elem + T + , empty : T + , method isEmpty : T -> [] Bool + , method insert : T -> Elem -> [] T + , method remove : T -> Elem -> [] T + , method member : T -> Elem -> [] Bool + , method foldl : {type A,E} -> T -> (Elem -> A -> [|E] A) -> A -> [|E] A + , method foldr : {type A,E} -> T -> (Elem -> A -> [|E] A) -> A -> [|E] A + , method toList : T -> [] List Elem + , method union : T -> T -> [] T + , method intersection : T -> T -> [] T + , method diffrence : T -> T -> [] T + , method eq : T -> T -> [] Bool + , method subset : T -> T -> [] Bool + , method partionLt : T -> Elem -> [] (Pair T T) + , method partionGt : T -> Elem -> [] (Pair T T) + , method range : T -> Interval Elem -> Interval Elem -> [] T + , method least : T -> [] Option Elem + , method greatest : T -> [] Option Elem + , method leastGt : T -> Elem -> [] Option Elem + , method leastGeq : T -> Elem -> [] Option Elem + , method greatestLt : T -> Elem -> [] Option Elem + , method greatestLeq : T -> Elem -> [] Option Elem } (** Red black tree implementation *) @@ -37,178 +37,207 @@ pub data Set Elem = Set of { data rec Q Val = Nil | E of Val , Q Val | T of Tree Val , Q Val let rec eqMain eq qs1 qs2 = - match (qs1,qs2) with + match (qs1,qs2) with | (Nil,Nil) => True + | (Nil, E _ _) => False + | (E _ _, Nil) => False + | (T Leaf rest, _) => eqMain eq rest qs2 + | (_, T Leaf rest) => eqMain eq qs1 rest + | (T (Node {left, value = elem, right}) rest, _) => eqMain eq (T left (E elem (T right rest))) qs2 + | (_, T (Node {left, value = elem, right}) rest) => eqMain eq qs1 (T left (E elem (T right rest))) + | (E elem1 rest1, E elem2 rest2) => match eq elem1 elem2 with - | Noteq => False - | Eq => eqMain eq rest1 rest2 + | Noteq => False + | Eq => eqMain eq rest1 rest2 end - end + end let rec subsetMain comp qs1 qs2 = - match (qs1,qs2) with + match (qs1,qs2) with | (Nil,_) => True + | (E _ _ , Nil) => False + | (T Leaf rest, _) => subsetMain comp rest qs2 + | (_ , T Leaf rest) => subsetMain comp qs1 rest + | (T (Node {left, value = elem, right}) rest, _) => subsetMain comp (T left (E elem (T right rest))) qs2 + | (_, T (Node {left, value = elem, right}) rest) => subsetMain comp qs1 (T left (E elem (T right rest))) + | (E elem1 rest1, E elem2 rest2) => match comp elem1 elem2 with - | Less => False - | Equal => subsetMain comp rest1 rest2 - | Greater => subsetMain comp qs1 rest2 + | Less => False + | Equal => subsetMain comp rest1 rest2 + | Greater => subsetMain comp qs1 rest2 end - end + end -let partionLt compare = fn tree key1 => let (_,left,right) = - split (fn key2 => match compare key1 key2 with - | Greater => Greater | _ => Less end) tree in (left,right) +let partionLt compare = fn tree key1 => + let (_,left,right) = + split + (fn key2 => + match compare key1 key2 with + | Greater => Greater + | _ => Less + end) + tree + in (left,right) -let partionGt compare = fn tree key1 => let (_, left,right) = - split (fn key2 => match compare key1 key2 with - | Less => Less | _ => Greater end) tree in (left,right) +let partionGt compare = fn tree key1 => + let (_, left,right) = + split + (fn key2 => + match compare key1 key2 with + | Less => Less + | _ => Greater + end) + tree + in (left,right) let rec least tree = - match tree with - | Leaf => None - | Node {left = Leaf, value = x} => Some x - | Node {left} => least left - end + match tree with + | Leaf => None + | Node {left = Leaf, value = x} => Some x + | Node {left} => least left + end let rec greatest tree = - match tree with - | Leaf => None - | Node {value = x, right = Leaf} => Some x - | Node {right} => greatest right - end + match tree with + | Leaf => None + | Node {value = x, right = Leaf} => Some x + | Node {right} => greatest right + end let empty = Leaf let isEmpty tree = - match tree with + match tree with | Leaf => True | _ => False - end + end let rec member compare tree elem = - match tree with + match tree with | Leaf => False | Node {left, value, right} => match compare elem value with - | Less => member compare left elem - | Greater => member compare right elem - | Equal => True + | Less => member compare left elem + | Greater => member compare right elem + | Equal => True end - end + end let insert compare tree elem = - match search (fn val => compare elem val) tree [] with + match search (fn val => compare elem val) tree [] with | (Leaf,zipper) => zipRed elem Leaf Leaf zipper | (Node ,_) => tree - end + end let remove compare tree elem = - match search (fn val => compare elem val) tree [] with + match search (fn val => compare elem val) tree [] with | (Leaf,_) => tree | (Node {color, left, right},zipper) => delete color left right zipper - end + end let rec _search compare tree elem = - match tree with - | Leaf => False - | Node {left, value, right} => - match compare elem value with + match tree with + | Leaf => False + | Node {left, value, right} => + match compare elem value with | Less => _search compare left elem | Greater => _search compare right elem | Equal => True - end - end + end + end let rec setFoldl tree func acc = - match tree with + match tree with | Leaf => acc | Node {left, value, right} => setFoldl right func (func value (setFoldl left func acc)) - end + end let rec setFoldr tree func acc = - match tree with + match tree with | Leaf => acc | Node {left, value, right} => setFoldr left func (func value (setFoldr right func acc)) - end + end let rec toList tree acc = - match tree with + match tree with | Leaf => acc | Node {left, value, right} => toList left (value :: toList right acc) - end + end let rec union compare tree1 tree2 = - match tree1 with + match tree1 with | Leaf => tree2 | Node {left = left1, value = key1, right = right1} => - match tree2 with + match tree2 with | Leaf => tree1 | Node => - let (_,left2,right2) = split (fn key2 => - compare key1 key2) tree2 in joinVal (union compare left1 left2) - key1 (union compare right1 right2) - end - end + let (_,left2,right2) = split (fn key2 => compare key1 key2) tree2 in + joinVal (union compare left1 left2) key1 + (union compare right1 right2) + end + end let rec intersection compare tree1 tree2 = - match tree1 with + match tree1 with | Leaf => Leaf | Node {left = left1, value = key1, right = right1} => - match tree2 with + match tree2 with | Leaf => Leaf | _ => let (value_out, left2, right2) = split (fn key2 => compare key1 key2) tree2 in let left = intersection compare left1 left2 in let right = intersection compare right1 right2 - in match value_out with - | Some _ => joinVal left key1 right - | None => join left right + in + match value_out with + | Some _ => joinVal left key1 right + | None => join left right end - end - end + end + end let rec diffrence compare tree1 tree2 = - match tree1 with + match tree1 with | Leaf => Leaf | Node {left = left1, value = key1, right = right1} => match tree2 with - | Leaf => tree1 - | _ => - let (value_out, left2, right2) = - split (fn key2 => compare key1 key2) tree2 - in let left = diffrence compare left1 left2 - in let right = diffrence compare right1 right2 - in match value_out with - | Some _ => join left right - | None => joinVal left key1 right - end + | Leaf => tree1 + | _ => + let (value_out, left2, right2) = + split (fn key2 => compare key1 key2) tree2 + in let left = diffrence compare left1 left2 + in let right = diffrence compare right1 right2 + in + match value_out with + | Some _ => join left right + | None => joinVal left key1 right + end end - end + end let subset compare set1 set2 = subsetMain compare (T set1 Nil) (T set2 Nil) let range compare tree left right = - match (left,right) with + match (left,right) with | (Inclusion left, Inclusion right) => let (_, tree') = partionLt compare tree left in let (tree'',_) = partionGt compare tree' right in tree'' @@ -221,89 +250,92 @@ let range compare tree left right = | (Exclusion left, Exclusion right) => let (_, tree') = partionGt compare tree left in let (tree'',_) = partionLt compare tree' right in tree'' - end + end let rec leastGt compare tree val = - match tree with - | Leaf => None - | Node {left, value = key, right} => - match compare val key with + match tree with + | Leaf => None + | Node {left, value = key, right} => + match compare val key with | Less => let x = leastGt compare left val in match x with - | None => Some key - | _ => x + | None => Some key + | _ => x end | Equal => least right | Greater => leastGt compare right val - end - end + end + end let rec leastGeq compare tree val = - match tree with - | Leaf => None - | Node {left, value = key, right} => - match compare val key with - | Less => match leastGeq compare left val with - | None => Some key - | x => x + match tree with + | Leaf => None + | Node {left, value = key, right} => + match compare val key with + | Less => + match leastGeq compare left val with + | None => Some key + | x => x end | Equal => Some val | Greater => leastGeq compare right val - end - end + end + end let rec greatestLt compare tree val = - match tree with + match tree with | Leaf => None | Node {left, value = key, right} => match compare val key with - | Less => greatestLt compare left val - | Equal => greatest left - | Greater => match greatestLt compare right val with - | None => Some key - | x => x - end + | Less => greatestLt compare left val + | Equal => greatest left + | Greater => + match greatestLt compare right val with + | None => Some key + | x => x + end end - end + end let rec greatestLeq compare tree val = - match tree with + match tree with | Leaf => None | Node {left, value = key, right} => match compare val key with - | Less => greatestLeq compare left val - | Equal => Some val - | Greater => match greatestLeq compare right val with - | None => Some key - | x => x - end + | Less => greatestLeq compare left val + | Equal => Some val + | Greater => + match greatestLeq compare right val with + | None => Some key + | x => x + end end - end + end pub let make {Val} (compare : Val -> Val -> [] Ordered) = Set { - T = Tree Val - , empty = empty - , method isEmpty = isEmpty - , method insert = insert compare - , method remove = remove compare - , method member = member compare - , method foldl = setFoldl - , method foldr = setFoldr - , method toList = fn tree => toList tree [] - , method union = union compare - , method intersection = intersection compare - , method diffrence = diffrence compare - , method eq = fn set1 set2 => - eqMain (fn e1 e2 => (compare e1 e2).toComparable) (T set1 Nil) (T set2 Nil) - , method subset = subset compare - , method partionLt = partionLt compare - , method partionGt = partionGt compare - , method range = range compare - , method least = least - , method greatest = greatest - , method leastGt = leastGt compare - , method leastGeq = leastGeq compare - , method greatestLt = greatestLt compare - , method greatestLeq = greatestLeq compare + T = Tree Val + , empty = empty + , method isEmpty = isEmpty + , method insert = insert compare + , method remove = remove compare + , method member = member compare + , method foldl = setFoldl + , method foldr = setFoldr + , method toList = fn tree => toList tree [] + , method union = union compare + , method intersection = intersection compare + , method diffrence = diffrence compare + , method eq = fn set1 set2 => + eqMain (fn e1 e2 => (compare e1 e2).toComparable) (T set1 Nil) (T set2 Nil) + , method subset = subset compare + , method partionLt = partionLt compare + , method partionGt = partionGt compare + , method range = range compare + , method least = least + , method greatest = greatest + , method leastGt = leastGt compare + , method leastGeq = leastGeq compare + , method greatestLt = greatestLt compare + , method greatestLeq = greatestLeq compare } From bb826df02e002f19147567762942e70f8b385692 Mon Sep 17 00:00:00 2001 From: Jakub Chomiczewski Date: Fri, 29 Nov 2024 00:57:19 +0100 Subject: [PATCH 13/27] Changing tests and adding assert to prelude --- lib/Prelude.fram | 3 ++ lib/Set.fram | 10 +++--- test/stdlib/stdlib0001_Map.fram | 56 +++++++++++++++---------------- test/stdlib/stdlib0002_Set.fram | 56 ++++++++++++++----------------- test/stdlib/stdlib0003_Queue.fram | 10 +++--- 5 files changed, 66 insertions(+), 69 deletions(-) diff --git a/lib/Prelude.fram b/lib/Prelude.fram index 383ba95d..330b32ac 100644 --- a/lib/Prelude.fram +++ b/lib/Prelude.fram @@ -43,3 +43,6 @@ pub module Int64 pub let one = 1L pub let ofInt (n : Int) = n.toInt64 end + +pub let assert condition msg = + if condition then () else ((printStrLn msg) ; exit 1) \ No newline at end of file diff --git a/lib/Set.fram b/lib/Set.fram index 89e423ed..5d3f6d90 100644 --- a/lib/Set.fram +++ b/lib/Set.fram @@ -18,7 +18,7 @@ pub data Set Elem = Set of { , method toList : T -> [] List Elem , method union : T -> T -> [] T , method intersection : T -> T -> [] T - , method diffrence : T -> T -> [] T + , method difference : T -> T -> [] T , method eq : T -> T -> [] Bool , method subset : T -> T -> [] Bool , method partionLt : T -> Elem -> [] (Pair T T) @@ -215,7 +215,7 @@ let rec intersection compare tree1 tree2 = end end -let rec diffrence compare tree1 tree2 = +let rec difference compare tree1 tree2 = match tree1 with | Leaf => Leaf | Node {left = left1, value = key1, right = right1} => @@ -224,8 +224,8 @@ let rec diffrence compare tree1 tree2 = | _ => let (value_out, left2, right2) = split (fn key2 => compare key1 key2) tree2 - in let left = diffrence compare left1 left2 - in let right = diffrence compare right1 right2 + in let left = difference compare left1 left2 + in let right = difference compare right1 right2 in match value_out with | Some _ => join left right @@ -325,7 +325,7 @@ pub let make {Val} (compare : Val -> Val -> [] Ordered) = Set { , method toList = fn tree => toList tree [] , method union = union compare , method intersection = intersection compare - , method diffrence = diffrence compare + , method difference = difference compare , method eq = fn set1 set2 => eqMain (fn e1 e2 => (compare e1 e2).toComparable) (T set1 Nil) (T set2 Nil) , method subset = subset compare diff --git a/test/stdlib/stdlib0001_Map.fram b/test/stdlib/stdlib0001_Map.fram index 6f56375f..235e6975 100644 --- a/test/stdlib/stdlib0001_Map.fram +++ b/test/stdlib/stdlib0001_Map.fram @@ -3,9 +3,6 @@ import open List import open Ordered import open Prelude -let assert condition = -if condition then () else exit 1 - let lt (v1 : Int) (v2 : Int) = if v1 < v2 then Less else if v2 < v1 then Greater @@ -20,63 +17,66 @@ let y = x.insert 1 1 let z = x.insert 1 "a" (* isEmpty check *) -let _ = assert (y.isEmpty == False) -let _ = assert (z.isEmpty == False) -let _ = assert (y.remove 1 >. isEmpty) +let _ = assert (y.isEmpty == False) "Failed isEmpty" +let _ = assert (z.isEmpty == False) "Failed isEmpty" +let _ = assert (y.remove 1 >. isEmpty) "Failed isEmpty" (* domain check *) -let z = y.insert 2 1 >. insert 3 2 >. insert 4 3 -let _ = assert (z.domain == [1,2,3,4] && z.toValueList == [1,1,2,3]) +let z = y.insert 2 1 >. insert 3 2 >. insert 4 3 +let _ = assert (z.domain == [1,2,3,4] && z.toValueList == [1,1,2,3]) "Failed domain" (* toList check *) let _ = assert ((z.toList.foldLeft - (fn acc (key,val) => val :: acc) []) == [1,1,2,3].rev) + (fn acc (key,val) => val :: acc) []) == [1,1,2,3].rev) "Failed toList" (* foldl check *) let _ = assert (z.foldl (fn key val acc => key :: acc) [] == [1,2,3,4].rev) + "Failed foldl" (* member check *) -let _ = assert (z.member 1) +let _ = assert (z.member 1) "Failed member" (* find check *) -let _ = assert (match z.find 1 with | None => False | _ => True end) +let _ = assert (match z.find 1 with | None => False | _ => True end) "Failed find" (* operate change check *) let _ = assert (snd (z.operate 1 (fn () => Some 2) (fn a => Some 0)) - >. toValueList == [0,1,2,3]) + >. toValueList == [0,1,2,3]) "Failed operate" (* operate add check *) let _ = assert (snd (z.operate 0 (fn () => Some 2) (fn a => Some 0)) - >. toValueList == [2,1,1,2,3]) + >. toValueList == [2,1,1,2,3]) "Failed operate" (* map check *) -let _ = assert (z.map (fn x => if x == x.shiftr 1 >. shiftl 1 then -x else x) - >. toValueList == [1,1,(0-2),3]) +let _ = assert (z.mapVal (fn x => if x == x.shiftr 1 >. shiftl 1 then -x else x) + >. toValueList == [1,1,(0-2),3]) "Failed map" (* union check *) let y = x.insert 1.neg 2 >. insert 2.neg 3 >. insert 0 1 >. insert 1 10 let w = z.union y (fn key val1 val2 => val2) -let _ = assert (w.toValueList == [3,2,1,10,1,2,3]) +let _ = assert (w.toValueList == [3,2,1,10,1,2,3]) "Failed union" (* partion check *) let q = w.partion 0 -let _ = assert (fst (fst q) >. toValueList == [3,2]) -let _ = assert (snd q >. toValueList == [10,1,2,3]) +let _ = assert (fst (fst q) >. toValueList == [3,2]) "Failed partion" +let _ = assert (snd q >. toValueList == [10,1,2,3]) "Failed partion" (* partionLt check *) let q = w.partionLt 0 -let _ = assert (fst q >. toValueList == [3,2,1]) -let _ = assert (snd q >. toValueList == [10,1,2,3]) +let _ = assert (fst q >. toValueList == [3,2,1]) "Failed partionLt" +let _ = assert (snd q >. toValueList == [10,1,2,3]) "Failed partionLt" (* partionGt check *) let q = w.partionGt 0 -let _ = assert (fst q >. toValueList == [3,2]) -let _ = assert (snd q >. toValueList == [1,10,1,2,3]) +let _ = assert (fst q >. toValueList == [3,2]) "Failed partionGt" +let _ = assert (snd q >. toValueList == [1,10,1,2,3]) "Failed partionGt" -(* rangeee check *) -let q = w.range (Exclusion 0) (Exclusion 2) -let _ = assert (q.toValueList == [10]) +(* range check *) +let q = w.range (Exclusion 0) (Exclusion 2) +let _ = assert (q.toValueList == [10]) "Failed range" let q = w.range (Inclusion 0) (Inclusion 2) -let _ = assert (q.toValueList == [1,10,1]) -let _ = assert (w.range (Inclusion 0) (Exclusion 2) >. toValueList == [1,10]) -let _ = assert (w.range (Exclusion 0) (Inclusion 2) >. toValueList == [10,1]) +let _ = assert (q.toValueList == [1,10,1]) "Failed range" +let _ = assert (w.range (Inclusion 0) (Exclusion 2) >. toValueList == [1,10]) + "Failed range" +let _ = assert (w.range (Exclusion 0) (Inclusion 2) >. toValueList == [10,1]) + "Failed range" diff --git a/test/stdlib/stdlib0002_Set.fram b/test/stdlib/stdlib0002_Set.fram index f64fd038..a9f2b877 100644 --- a/test/stdlib/stdlib0002_Set.fram +++ b/test/stdlib/stdlib0002_Set.fram @@ -3,9 +3,6 @@ import open List import open Ordered import open Prelude -let assert condition = -if condition then () else exit 1 - let lt (v1 : Int) (v2 : Int) = if v1 < v2 then Less else if v2 < v1 then Greater @@ -15,63 +12,62 @@ let Set.Set {module IntSet} = Set.make lt (* empty check *) let x = IntSet.empty -let _ = assert (x.isEmpty) - -(* singletonSet check depricated *) -(*let x = 0.singletonSet -let _ = assert (not x.isEmpty)*) +let _ = assert (x.isEmpty) "Failed empty" let x = x.insert 0 (* toList check *) -let _ = assert (x.toList == [0]) +let _ = assert (x.toList == [0]) "Failed toList" (* insert check *) let y = x.insert 1 -let _ = assert (y.toList == [0,1]) -let _ = assert (y.insert 2 >. toList == [0,1,2]) +let _ = assert (y.toList == [0,1]) "Failed insert" +let _ = assert (y.insert 2 >. toList == [0,1,2]) "Failed insert" (* remove check *) -let y = y.insert 2 >. insert 3 -let _ = assert (y.remove 1 >. toList == [0,2,3]) +let y = y.insert 2 >. insert 3 +let _ = assert (y.remove 1 >. toList == [0,2,3]) "Failed remove" (* member check *) -let _ = assert (y.member 1) -let _ = assert (not (y.member 10)) +let _ = assert (y.member 1) "Failed check" +let _ = assert (not (y.member 10)) "Failed check" (* foldl/r check *) -let _ = assert (y.foldl (fn x acc => x + acc) 0 == 6) -let _ = assert (y.foldr (fn x acc => x + acc) 0 == 6) +let _ = assert (y.foldl (fn x acc => x + acc) 0 == 6) "Failed foldl" +let _ = assert (y.foldr (fn x acc => x + acc) 0 == 6) "Failed foldr" (* union check *) let x = x.insert 4 >. insert 5 >. insert 6 -let _ = (y.union x >. toList == [0,1,2,3,4,5,6]) +let _ = assert (y.union x >. toList == [0,1,2,3,4,5,6]) "Failed union" (* intersection check *) -let _ = assert (x.intersection y >. toList == [0]) +let _ = assert (x.intersection y >. toList == [0]) "Failed intersection" (* diffrence check *) -let _ = assert (y.diffrence x >. toList == [1,2,3]) -let _ = assert (x.diffrence y >. toList == [4,5,6]) +let _ = assert (y.difference x >. toList == [1,2,3]) "Failed difference" +let _ = assert (x.difference y >. toList == [4,5,6]) "Failed difference" (* eq check *) -let _ = assert (x.eq x) -let _ = assert (not (x.eq y)) +let _ = assert (x.eq x) "Failed eq" +let _ = assert (not (x.eq y)) "Failed eq" (* subset check *) -let _ = assert (IntSet.empty.subset x) -let _ = assert (IntSet.empty.insert 0 >. insert 1 >. subset y) -let _ = assert (not (x.subset y)) +let _ = assert (IntSet.empty.subset x) "Failed subset" +let _ = assert (IntSet.empty.insert 0 >. insert 1 >. subset y) "Failed subset" +let _ = assert (not (x.subset y)) "Failed subset" (* partionLt check *) -let _ = assert (fst (y.partionLt 2) >. toList == [0,1]) -let _ = assert (snd (y.partionLt 2) >. toList == [2,3]) +let _ = assert (fst (y.partionLt 2) >. toList == [0,1]) "Failed partionLt" +let _ = assert (snd (y.partionLt 2) >. toList == [2,3]) "Failed partionLt" (* range check *) -let _ = assert (y.range (Inclusion 1) (Inclusion 2) >. toList == [1,2]) +let _ = + assert (y.range (Inclusion 1) (Inclusion 2) >. toList == [1,2]) "Failed range" (* least check *) -let _ = assert (match y.least with | Some x => x == 0 | _ => False end) +let _ = + assert (match y.least with | Some x => x == 0 | _ => False end) "Failed least" (* greatest check *) let _ = assert (match y.greatest with | Some x => x == 3 | _ => False end) + "Failed greatest" diff --git a/test/stdlib/stdlib0003_Queue.fram b/test/stdlib/stdlib0003_Queue.fram index 49d8ef04..ac163ebe 100644 --- a/test/stdlib/stdlib0003_Queue.fram +++ b/test/stdlib/stdlib0003_Queue.fram @@ -1,7 +1,5 @@ import Queue - -let assert condition = -if condition then () else exit 1 +import Prelude let compare (x : Int) (y : Int) = x == y let get_val x = @@ -12,10 +10,10 @@ end let x = Queue.emptyQueue let x = x.push 1 -let _ = assert (x.isEmpty == False && compare (get_val x.head) 1) +let _ = assert (x.isEmpty == False && compare (get_val x.head) 1) "Failed push" let x = x.pop -let _ = assert x.isEmpty +let _ = assert x.isEmpty "Failed isEmpty" let x = x >. push 1 >. push 2 >. push 3 let _ = assert (x.isEmpty == False && compare (get_val x.head) 1 && compare (get_val (x.pop >. head)) 2 && - compare (get_val (x.pop >. pop >. head)) 3) + compare (get_val (x.pop >. pop >. head)) 3) "Failed head and pop" From a3f0b7b86f382a711bfc2b01f6ec5006c4e1d4ba Mon Sep 17 00:00:00 2001 From: Jakub Chomiczewski Date: Sat, 30 Nov 2024 15:37:41 +0100 Subject: [PATCH 14/27] little changes --- lib/Ordered.fram | 37 ++++++++++++++++++++++++++++++++ lib/Queue.fram | 55 ++++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 92 insertions(+) diff --git a/lib/Ordered.fram b/lib/Ordered.fram index dd45c213..19e4d01d 100644 --- a/lib/Ordered.fram +++ b/lib/Ordered.fram @@ -14,3 +14,40 @@ pub data Interval Value = Inclusion of Value | Exclusion of Value pub let ordToComp elem = match elem with | Equal => Eq | _ => Noteq end pub method toComparable {self : Ordered} = ordToComp self + +pub let getIntervalList pairInterval compare travers struct = + match pairInterval with + | Inclusion v1, Inclusion v2 => + travers (fn x acc => + match (compare v1 x, compare x v2) with + | (Equal, Less) => x :: acc + | (Equal, Equal) => x :: acc + | (Greater, Equal) => x :: acc + | (Greater, Less) => x :: acc + | _ => acc + end + ) struct [] + | Inclusion v1, Exclusion v2 => + travers (fn x acc => + match (compare v1 x, compare x v2) with + | (Equal, Less) => x :: acc + | (Greater, Less) => x :: acc + | _ => acc + end + ) struct [] + | Exclusion v1, Inclusion v2 => + travers (fn x acc => + match (compare v1 x, compare x v2) with + | (Greater,Less) => x :: acc + | (Greater,Equal) => x :: acc + | _ => acc + end + ) struct [] + | Exclusion v1, Exclusion v2 => + travers (fn x acc => + match (compare v1 x, compare x v2) with + | (Greater,Less) => x :: acc + | _ => acc + end + ) struct [] + end \ No newline at end of file diff --git a/lib/Queue.fram b/lib/Queue.fram index 86f87913..3b0cb002 100644 --- a/lib/Queue.fram +++ b/lib/Queue.fram @@ -2,6 +2,8 @@ * See LICENSE for details. *) +import List + data NotNegativeInt = Zero | Positive of Int let addOne value = @@ -106,6 +108,57 @@ let tail queue = check (HMQueue (subOne lenf) xs (invalidate state) lenr r) end +let foldlRotationState f acc state = + match state with + | Idle => acc + | Done list => List.foldLeft f acc list + | Appending _ list1 list2 => + List.foldLeft f + (List.foldLeft f acc list2) + list1 + | Reversing _ list1 list2 list3 list4 => + List.foldLeft f + (List.foldLeft f + (List.foldLeft f + (List.foldLeft f acc list4) + list3 + ) + list2 + ) + list1 + end + +pub let foldlQueue queue f acc = + match queue with + | HMQueue _ list1 state _ list2 => + List.foldLeft f + (foldlRotationState f + (List.foldLeft f acc list1) + state + ) + list1 + end + +let mapRotationState f state = + match state with + | Idle => Idle + | Done list => Done (List.map f list) + | Appending v list1 list2 => + Appending v (List.map f list1) (List.map f list2) + | Reversing v list1 list2 list3 list4 => + Reversing v (List.map f list1) (List.map f list2) + (List.map f list3) (List.map f list4) + end + +let mapQueue queue f = + match queue with + | HMQueue v1 list1 state v2 list2 => + HMQueue v1 (List.map f list1) + (mapRotationState f state) v2 + (List.map f list2) + end + +pub let fromList list = List.foldLeft snoc emptyQueue list pub method isEmpty = isEmpty self pub method snoc = snoc self @@ -113,3 +166,5 @@ pub method tail = tail self pub method push = snoc self pub method pop = tail self pub method head = head self +pub method foldl = foldlQueue self +pub method map = mapQueue self From c44f26ccb442eaed2b0fa3aa33fae4be60edf539 Mon Sep 17 00:00:00 2001 From: Jakub Chomiczewski Date: Tue, 3 Dec 2024 12:02:39 +0100 Subject: [PATCH 15/27] Moving things from Ord and adding fromList and toList to Queue --- lib/Map.fram | 2 ++ lib/Ordered.fram | 53 ------------------------------- lib/Prelude.fram | 13 +++++++- lib/Queue.fram | 10 ++++-- lib/RedBlackTree.fram | 2 +- lib/Set.fram | 2 ++ test/stdlib/stdlib0001_Map.fram | 9 +++--- test/stdlib/stdlib0002_Set.fram | 3 +- test/stdlib/stdlib0003_Queue.fram | 3 ++ 9 files changed, 33 insertions(+), 64 deletions(-) delete mode 100644 lib/Ordered.fram diff --git a/lib/Map.fram b/lib/Map.fram index c40f7177..f5457823 100644 --- a/lib/Map.fram +++ b/lib/Map.fram @@ -6,6 +6,8 @@ import open RedBlackTree (** Signature *) +pub data Interval Value = Inclusion of Value | Exclusion of Value + pub data Map Key = Map of { T , empty : {type Val} -> T Val diff --git a/lib/Ordered.fram b/lib/Ordered.fram deleted file mode 100644 index 19e4d01d..00000000 --- a/lib/Ordered.fram +++ /dev/null @@ -1,53 +0,0 @@ -(* This file is part of DBL, released under MIT license. - * See LICENSE for details. -*) - -pub data Comparable = Eq| Noteq - -pub data Ordered = -| Less -| Equal -| Greater - -pub data Interval Value = Inclusion of Value | Exclusion of Value - -pub let ordToComp elem = match elem with | Equal => Eq | _ => Noteq end - -pub method toComparable {self : Ordered} = ordToComp self - -pub let getIntervalList pairInterval compare travers struct = - match pairInterval with - | Inclusion v1, Inclusion v2 => - travers (fn x acc => - match (compare v1 x, compare x v2) with - | (Equal, Less) => x :: acc - | (Equal, Equal) => x :: acc - | (Greater, Equal) => x :: acc - | (Greater, Less) => x :: acc - | _ => acc - end - ) struct [] - | Inclusion v1, Exclusion v2 => - travers (fn x acc => - match (compare v1 x, compare x v2) with - | (Equal, Less) => x :: acc - | (Greater, Less) => x :: acc - | _ => acc - end - ) struct [] - | Exclusion v1, Inclusion v2 => - travers (fn x acc => - match (compare v1 x, compare x v2) with - | (Greater,Less) => x :: acc - | (Greater,Equal) => x :: acc - | _ => acc - end - ) struct [] - | Exclusion v1, Exclusion v2 => - travers (fn x acc => - match (compare v1 x, compare x v2) with - | (Greater,Less) => x :: acc - | _ => acc - end - ) struct [] - end \ No newline at end of file diff --git a/lib/Prelude.fram b/lib/Prelude.fram index 330b32ac..b524e84d 100644 --- a/lib/Prelude.fram +++ b/lib/Prelude.fram @@ -45,4 +45,15 @@ pub module Int64 end pub let assert condition msg = - if condition then () else ((printStrLn msg) ; exit 1) \ No newline at end of file + if condition then () else ((printStrLn msg) ; exit 1) + +pub data Comparable = Eq| Noteq + +pub data Ordered = +| Less +| Equal +| Greater + +pub let ordToComp elem = match elem with | Equal => Eq | _ => Noteq end + +pub method toComparable {self : Ordered} = ordToComp self diff --git a/lib/Queue.fram b/lib/Queue.fram index 3b0cb002..6d41106e 100644 --- a/lib/Queue.fram +++ b/lib/Queue.fram @@ -136,7 +136,7 @@ pub let foldlQueue queue f acc = (List.foldLeft f acc list1) state ) - list1 + list2 end let mapRotationState f state = @@ -158,6 +158,12 @@ let mapQueue queue f = (List.map f list2) end +let rec toList queue = + match head queue with + | None => [] + | Some x => x :: toList (tail queue) + end + pub let fromList list = List.foldLeft snoc emptyQueue list pub method isEmpty = isEmpty self @@ -166,5 +172,5 @@ pub method tail = tail self pub method push = snoc self pub method pop = tail self pub method head = head self -pub method foldl = foldlQueue self pub method map = mapQueue self +pub method toList = toList self diff --git a/lib/RedBlackTree.fram b/lib/RedBlackTree.fram index baec3efb..bb75005e 100644 --- a/lib/RedBlackTree.fram +++ b/lib/RedBlackTree.fram @@ -2,7 +2,7 @@ * See LICENSE for details. *) -import open Ordered +import open Prelude import List data Color = diff --git a/lib/Set.fram b/lib/Set.fram index 5d3f6d90..3ce35601 100644 --- a/lib/Set.fram +++ b/lib/Set.fram @@ -6,6 +6,8 @@ import open RedBlackTree (** Signature of Set *) +pub data Interval Value = Inclusion of Value | Exclusion of Value + pub data Set Elem = Set of { T , empty : T diff --git a/test/stdlib/stdlib0001_Map.fram b/test/stdlib/stdlib0001_Map.fram index 235e6975..01c19835 100644 --- a/test/stdlib/stdlib0001_Map.fram +++ b/test/stdlib/stdlib0001_Map.fram @@ -1,6 +1,5 @@ import Map import open List -import open Ordered import open Prelude let lt (v1 : Int) (v2 : Int) = @@ -72,11 +71,11 @@ let _ = assert (fst q >. toValueList == [3,2]) "Failed partionGt" let _ = assert (snd q >. toValueList == [1,10,1,2,3]) "Failed partionGt" (* range check *) -let q = w.range (Exclusion 0) (Exclusion 2) +let q = w.range (Map.Exclusion 0) (Map.Exclusion 2) let _ = assert (q.toValueList == [10]) "Failed range" -let q = w.range (Inclusion 0) (Inclusion 2) +let q = w.range (Map.Inclusion 0) (Map.Inclusion 2) let _ = assert (q.toValueList == [1,10,1]) "Failed range" -let _ = assert (w.range (Inclusion 0) (Exclusion 2) >. toValueList == [1,10]) +let _ = assert (w.range (Map.Inclusion 0) (Map.Exclusion 2) >. toValueList == [1,10]) "Failed range" -let _ = assert (w.range (Exclusion 0) (Inclusion 2) >. toValueList == [10,1]) +let _ = assert (w.range (Map.Exclusion 0) (Map.Inclusion 2) >. toValueList == [10,1]) "Failed range" diff --git a/test/stdlib/stdlib0002_Set.fram b/test/stdlib/stdlib0002_Set.fram index a9f2b877..7dc35c07 100644 --- a/test/stdlib/stdlib0002_Set.fram +++ b/test/stdlib/stdlib0002_Set.fram @@ -1,6 +1,5 @@ import Set import open List -import open Ordered import open Prelude let lt (v1 : Int) (v2 : Int) = @@ -62,7 +61,7 @@ let _ = assert (snd (y.partionLt 2) >. toList == [2,3]) "Failed partionLt" (* range check *) let _ = - assert (y.range (Inclusion 1) (Inclusion 2) >. toList == [1,2]) "Failed range" + assert (y.range (Set.Inclusion 1) (Set.Inclusion 2) >. toList == [1,2]) "Failed range" (* least check *) let _ = diff --git a/test/stdlib/stdlib0003_Queue.fram b/test/stdlib/stdlib0003_Queue.fram index ac163ebe..159bfc34 100644 --- a/test/stdlib/stdlib0003_Queue.fram +++ b/test/stdlib/stdlib0003_Queue.fram @@ -1,5 +1,6 @@ import Queue import Prelude +import List let compare (x : Int) (y : Int) = x == y let get_val x = @@ -17,3 +18,5 @@ let x = x >. push 1 >. push 2 >. push 3 let _ = assert (x.isEmpty == False && compare (get_val x.head) 1 && compare (get_val (x.pop >. head)) 2 && compare (get_val (x.pop >. pop >. head)) 3) "Failed head and pop" +let x = Queue.fromList [1,2,3] +let _ = assert (x.toList == [1,2,3]) "Failed toList and fromList" \ No newline at end of file From b9eb957a1415d2e7404a617bddc9232ace6ba51a Mon Sep 17 00:00:00 2001 From: Jakub Chomiczewski Date: Tue, 3 Dec 2024 15:33:33 +0100 Subject: [PATCH 16/27] onError methods --- lib/Map.fram | 150 ++++++++++++++++++++++++++++++++++++++------------- lib/Set.fram | 78 ++++++++++++++++++++++----- 2 files changed, 180 insertions(+), 48 deletions(-) diff --git a/lib/Map.fram b/lib/Map.fram index f5457823..a56ec571 100644 --- a/lib/Map.fram +++ b/lib/Map.fram @@ -56,14 +56,34 @@ pub data Map Key = Map of { [] Pair (T Val) (T Val) , method range : {type Val} -> T Val -> Interval Key -> Interval Key -> [] T Val - , method least : {type Val} -> T Val -> [] Option (Pair Key Val) - , method greatest : {type Val} -> T Val -> [] Option (Pair Key Val) - , method leastGt : {type Val} -> T Val -> Key -> [] Option (Pair Key Val) - , method leastGeq : {type Val} -> T Val -> Key -> [] Option (Pair Key Val) - , method greatestLt : {type Val} -> T Val -> + , method lowerBound : {type Val} -> T Val -> [] Option (Pair Key Val) + , method lowerBoundErr : + {type Val, Err, ~onError : Unit -> [Err] (Pair Key Val)} -> + T Val -> [Err] (Pair Key Val) + , method upperBound : {type Val} -> T Val -> [] Option (Pair Key Val) + , method upperBoundErr : + {type Val, Err, ~onError : Unit -> [Err] (Pair Key Val)} -> + T Val -> [Err] (Pair Key Val) + , method lowerBoundGt : {type Val} -> T Val -> Key -> + [] Option (Pair Key Val) + , method lowerBoundGtErr : + {type Val, Err, ~onError : Unit -> [Err] (Pair Key Val)} -> + T Val -> Key -> [Err] (Pair Key Val) + , method lowerBoundGeq : {type Val} -> T Val -> Key -> + [] Option (Pair Key Val) + , method lowerBoundGeqErr : + {type Val, Err, ~onError : Unit -> [Err] (Pair Key Val)} -> + T Val -> Key -> [Err] (Pair Key Val) + , method upperBoundLt : {type Val} -> T Val -> Key -> [] Option (Pair Key Val) - , method greatestLeq : {type Val,E} -> T Val -> + , method upperBoundLtErr : + {type Val, Err, ~onError : Unit -> [Err] (Pair Key Val)} -> + T Val -> Key -> [Err] (Pair Key Val) + , method upperBoundLeq : {type Val,E} -> T Val -> Key -> [] Option (Pair Key Val) + , method upperBoundLeqErr : + {type Val, Err, ~onError : Unit -> [Err] (Pair Key Val)} -> + T Val -> Key -> [Err] (Pair Key Val) } (** implementation *) @@ -216,80 +236,116 @@ let partionGt compare tree key = in (left, right) -let rec least tree = +let rec lowerBound tree = match tree with | Leaf => None | Node {left = Leaf, value} => Some value - | Node {left} => least left + | Node {left} => lowerBound left end -let rec greatest tree = +let lowerBoundErr {~onError} tree = + match lowerBound tree with + | None => ~onError () + | Some x => x + end + +let rec upperBound tree = match tree with | Leaf => None | Node { value, right=Leaf} => Some value - | Node {right} => greatest right + | Node {right} => upperBound right end -let rec leastGt compare tree key = +let upperBoundErr {~onError} tree = + match upperBound tree with + | None => ~onError () + | Some x => x + end + +let rec lowerBoundGt compare tree key = match tree with | Leaf => None | Node {left, value = (key1, value), right} => match compare key key1 with | Less => - match leastGt compare left key with + match lowerBoundGt compare left key with | None => Some (key1, value) | x => x end - | Equal => least right - | Greater => leastGt compare right key + | Equal => lowerBound right + | Greater => lowerBoundGt compare right key end end -let rec leastGeq compare tree key = +let lowerBoundGtErr {~onError} compare tree key = + match lowerBoundGt compare tree key with + | None => ~onError () + | Some x => x + end + +let rec lowerBoundGeq compare tree key = match tree with | Leaf => None | Node {left, value = (key1, value), right} => match compare key key1 with | Less => - match leastGeq compare left key with + match lowerBoundGeq compare left key with | None => Some (key1,value) | x => x end | Equal => Some (key1, value) - | Greater => leastGeq compare right key + | Greater => lowerBoundGeq compare right key end end -let rec greatestLt compare tree key = +let lowerBoundGeqErr {~onError} compare tree key = + match lowerBoundGeq compare tree key with + | None => ~onError () + | Some x => x + end + +let rec upperBoundLt compare tree key = match tree with | Leaf => None | Node {left, value = (key1,value), right} => match compare key key1 with - | Less => greatestLt compare left key - | Equal => greatest left + | Less => upperBoundLt compare left key + | Equal => upperBound left | Greater => - match greatestLt compare right key with + match upperBoundLt compare right key with | None => Some (key1,value) | x => x end end end -let rec greatestLeq compare tree key = +let upperBoundLtErr {~onError} compare tree key = + match upperBoundLt compare tree key with + | None => ~onError () + | Some x => x + end + +let rec upperBoundLeq compare tree key = match tree with | Leaf => None | Node {left, value = (key1,value), right} => match compare key key1 with - | Less => greatestLt compare left key + | Less => upperBoundLt compare left key | Equal => Some (key1,value) | Greater => - match greatestLeq compare right key with + match upperBoundLeq compare right key with | None => Some (key1,value) | x => x end end end +let upperBoundLeqErr {~onError} compare tree key = + match upperBoundLeq compare tree key with + | None => ~onError () + | Some x => x + end + let toList tree = foldr (fn key value acc => (key, value) :: acc) tree [] let toValueList tree = foldr (fn key value acc => value :: acc) tree [] @@ -377,17 +433,33 @@ let partionGtT compare (MapT tree) key = let rangeT compare (MapT tree) left right = MapT (range compare tree left right) -let leastT (MapT tree) = least tree +let lowerBoundT (MapT tree) = lowerBound tree + +let lowerBoundTErr {~onError} (MapT tree) = lowerBoundErr tree + +let upperBoundT (MapT tree) = upperBound tree + +let upperBoundTErr {~onError} (MapT tree) = upperBoundErr tree + +let lowerBoundGtT compare (MapT tree) key = lowerBoundGt compare tree key + +let lowerBoundGtTErr {~onError} compare (MapT tree) key = + lowerBoundGtErr compare tree key + +let upperBoundLtT compare (MapT tree) key = upperBoundLt compare tree key -let greatest (MapT tree) = greatest tree +let upperBoundLtTErr {~onError} compare (MapT tree) key = + upperBoundLtErr compare tree key -let leastGtT compare (MapT tree) key = leastGt compare tree key +let lowerBoundGeqT compare (MapT tree) key = lowerBoundGeq compare tree key -let greatestLtT compare (MapT tree) key = greatestLt compare tree key +let lowerBoundGeqTErr {~onError} compare (MapT tree) key = + lowerBoundGeqErr compare tree key -let leastGeqT compare (MapT tree) key = leastGeq compare tree key +let upperBoundLeqT compare (MapT tree) key = upperBoundLeq compare tree key -let greatestLeqT compare (MapT tree) key = greatestLeq compare tree key +let upperBoundLeqTErr {~onError} compare (MapT tree) key = + upperBoundLeqErr compare tree key pub let make {Key} (compare : Key -> Key -> [] Ordered) = Map { T = MapT Key @@ -413,10 +485,16 @@ pub let make {Key} (compare : Key -> Key -> [] Ordered) = Map { , method partionLt = partionLtT compare , method partionGt = partionGtT compare , method range = rangeT compare - , method least = leastT - , method greatest = greatest - , method leastGt = leastGtT compare - , method leastGeq = leastGeqT compare - , method greatestLt = greatestLtT compare - , method greatestLeq = greatestLeqT compare + , method lowerBound = lowerBoundT + , method lowerBoundErr = lowerBoundTErr + , method upperBound = upperBoundT + , method upperBoundErr = upperBoundTErr + , method lowerBoundGt = lowerBoundGtT compare + , method lowerBoundGtErr = lowerBoundGtTErr compare + , method lowerBoundGeq = lowerBoundGeqT compare + , method lowerBoundGeqErr = lowerBoundGeqTErr compare + , method upperBoundLt = upperBoundLtT compare + , method upperBoundLtErr = upperBoundLtTErr compare + , method upperBoundLeq = upperBoundLeqT compare + , method upperBoundLeqErr = upperBoundLeqTErr compare } diff --git a/lib/Set.fram b/lib/Set.fram index 3ce35601..6988173c 100644 --- a/lib/Set.fram +++ b/lib/Set.fram @@ -26,12 +26,24 @@ pub data Set Elem = Set of { , method partionLt : T -> Elem -> [] (Pair T T) , method partionGt : T -> Elem -> [] (Pair T T) , method range : T -> Interval Elem -> Interval Elem -> [] T - , method least : T -> [] Option Elem - , method greatest : T -> [] Option Elem - , method leastGt : T -> Elem -> [] Option Elem - , method leastGeq : T -> Elem -> [] Option Elem - , method greatestLt : T -> Elem -> [] Option Elem - , method greatestLeq : T -> Elem -> [] Option Elem + , method lowerBound : T -> [] Option Elem + , method lowerBoundErr : + {Err, ~onError : Unit -> [Err] Elem} -> T -> [Err] Elem + , method upperBound : T -> [] Option Elem + , method upperBoundErr : + {Err, ~onError : Unit -> [Err] Elem} -> T -> [Err] Elem + , method lowerBoundGt : T -> Elem -> [] Option Elem + , method lowerBoundGtErr : + {Err, ~onError : Unit -> [Err] Elem} -> T -> Elem -> [Err] Elem + , method lowerBoundGeq : T -> Elem -> [] Option Elem + , method lowerBoundGeqErr : + {Err, ~onError : Unit -> [Err] Elem} -> T -> Elem -> [Err] Elem + , method upperBoundLt : T -> Elem -> [] Option Elem + , method upperBoundLtErr : + {Err, ~onError : Unit -> [Err] Elem} -> T -> Elem -> [Err] Elem + , method upperBoundLeq : T -> Elem -> [] Option Elem + , method upperBoundLeqErr : + {Err, ~onError : Unit -> [Err] Elem} -> T -> Elem -> [Err] Elem } (** Red black tree implementation *) @@ -116,6 +128,12 @@ let rec least tree = | Node {left} => least left end +let leastErr { ~onError } tree = + match least tree with + | None => ~onError () + | Some x => x + end + let rec greatest tree = match tree with | Leaf => None @@ -123,6 +141,12 @@ let rec greatest tree = | Node {right} => greatest right end +let greatestErr { ~onError } tree = + match greatest tree with + | None => ~onError () + | Some x => x + end + let empty = Leaf let isEmpty tree = @@ -269,6 +293,12 @@ let rec leastGt compare tree val = end end +let leastGtErr { ~onError } compare tree val = + match leastGt compare tree val with + | None => ~onError () + | Some x => x + end + let rec leastGeq compare tree val = match tree with | Leaf => None @@ -284,6 +314,12 @@ let rec leastGeq compare tree val = end end +let leastGeqErr { ~onError } compare tree val = + match leastGeq compare tree val with + | None => ~onError () + | Some x => x + end + let rec greatestLt compare tree val = match tree with | Leaf => None @@ -299,6 +335,12 @@ let rec greatestLt compare tree val = end end +let greatestLtErr { ~onError } compare tree val = + match greatestLt compare tree val with + | None => ~onError () + | Some x => x + end + let rec greatestLeq compare tree val = match tree with | Leaf => None @@ -314,6 +356,12 @@ let rec greatestLeq compare tree val = end end +let greatestLeqErr { ~onError } compare tree val = + match greatestLeq compare tree val with + | None => ~onError () + | Some x => x + end + pub let make {Val} (compare : Val -> Val -> [] Ordered) = Set { T = Tree Val @@ -334,10 +382,16 @@ pub let make {Val} (compare : Val -> Val -> [] Ordered) = Set { , method partionLt = partionLt compare , method partionGt = partionGt compare , method range = range compare - , method least = least - , method greatest = greatest - , method leastGt = leastGt compare - , method leastGeq = leastGeq compare - , method greatestLt = greatestLt compare - , method greatestLeq = greatestLeq compare + , method lowerBound = least + , method lowerBoundErr = leastErr + , method upperBound = greatest + , method upperBoundErr = greatestErr + , method lowerBoundGt = leastGt compare + , method lowerBoundGtErr = leastGtErr compare + , method lowerBoundGeq = leastGeq compare + , method lowerBoundGeqErr = leastGeqErr compare + , method upperBoundLt = greatestLt compare + , method upperBoundLtErr = greatestLtErr compare + , method upperBoundLeq = greatestLeq compare + , method upperBoundLeqErr = greatestLeqErr compare } From 88ee81d136a4b1e1fe57c712b00b1a1038326978 Mon Sep 17 00:00:00 2001 From: Jakub Chomiczewski Date: Tue, 3 Dec 2024 15:39:55 +0100 Subject: [PATCH 17/27] correcting test for names changes --- test/stdlib/stdlib0002_Set.fram | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/test/stdlib/stdlib0002_Set.fram b/test/stdlib/stdlib0002_Set.fram index 7dc35c07..4b313b23 100644 --- a/test/stdlib/stdlib0002_Set.fram +++ b/test/stdlib/stdlib0002_Set.fram @@ -63,10 +63,10 @@ let _ = assert (snd (y.partionLt 2) >. toList == [2,3]) "Failed partionLt" let _ = assert (y.range (Set.Inclusion 1) (Set.Inclusion 2) >. toList == [1,2]) "Failed range" -(* least check *) +(* lowerBound check *) let _ = - assert (match y.least with | Some x => x == 0 | _ => False end) "Failed least" + assert (match y.lowerBound with | Some x => x == 0 | _ => False end) "Failed lowerBound" -(* greatest check *) -let _ = assert (match y.greatest with | Some x => x == 3 | _ => False end) - "Failed greatest" +(* upperBound check *) +let _ = assert (match y.upperBound with | Some x => x == 3 | _ => False end) + "Failed upperBound" From 6727f662ff06985e3d2d84829c3d99ab438fdecd Mon Sep 17 00:00:00 2001 From: Jakub Chomiczewski Date: Tue, 3 Dec 2024 15:44:15 +0100 Subject: [PATCH 18/27] little change --- lib/Map.fram | 26 ++++++++++++++------------ lib/Set.fram | 14 ++++++++------ 2 files changed, 22 insertions(+), 18 deletions(-) diff --git a/lib/Map.fram b/lib/Map.fram index a56ec571..4f6a93c5 100644 --- a/lib/Map.fram +++ b/lib/Map.fram @@ -8,6 +8,8 @@ import open RedBlackTree pub data Interval Value = Inclusion of Value | Exclusion of Value +implicit ~onError + pub data Map Key = Map of { T , empty : {type Val} -> T Val @@ -243,7 +245,7 @@ let rec lowerBound tree = | Node {left} => lowerBound left end -let lowerBoundErr {~onError} tree = +let lowerBoundErr tree = match lowerBound tree with | None => ~onError () | Some x => x @@ -256,7 +258,7 @@ let rec upperBound tree = | Node {right} => upperBound right end -let upperBoundErr {~onError} tree = +let upperBoundErr tree = match upperBound tree with | None => ~onError () | Some x => x @@ -277,7 +279,7 @@ let rec lowerBoundGt compare tree key = end end -let lowerBoundGtErr {~onError} compare tree key = +let lowerBoundGtErr compare tree key = match lowerBoundGt compare tree key with | None => ~onError () | Some x => x @@ -298,7 +300,7 @@ let rec lowerBoundGeq compare tree key = end end -let lowerBoundGeqErr {~onError} compare tree key = +let lowerBoundGeqErr compare tree key = match lowerBoundGeq compare tree key with | None => ~onError () | Some x => x @@ -319,7 +321,7 @@ let rec upperBoundLt compare tree key = end end -let upperBoundLtErr {~onError} compare tree key = +let upperBoundLtErr compare tree key = match upperBoundLt compare tree key with | None => ~onError () | Some x => x @@ -340,7 +342,7 @@ let rec upperBoundLeq compare tree key = end end -let upperBoundLeqErr {~onError} compare tree key = +let upperBoundLeqErr compare tree key = match upperBoundLeq compare tree key with | None => ~onError () | Some x => x @@ -435,30 +437,30 @@ let rangeT compare (MapT tree) left right = let lowerBoundT (MapT tree) = lowerBound tree -let lowerBoundTErr {~onError} (MapT tree) = lowerBoundErr tree +let lowerBoundTErr (MapT tree) = lowerBoundErr tree let upperBoundT (MapT tree) = upperBound tree -let upperBoundTErr {~onError} (MapT tree) = upperBoundErr tree +let upperBoundTErr (MapT tree) = upperBoundErr tree let lowerBoundGtT compare (MapT tree) key = lowerBoundGt compare tree key -let lowerBoundGtTErr {~onError} compare (MapT tree) key = +let lowerBoundGtTErr compare (MapT tree) key = lowerBoundGtErr compare tree key let upperBoundLtT compare (MapT tree) key = upperBoundLt compare tree key -let upperBoundLtTErr {~onError} compare (MapT tree) key = +let upperBoundLtTErr compare (MapT tree) key = upperBoundLtErr compare tree key let lowerBoundGeqT compare (MapT tree) key = lowerBoundGeq compare tree key -let lowerBoundGeqTErr {~onError} compare (MapT tree) key = +let lowerBoundGeqTErr compare (MapT tree) key = lowerBoundGeqErr compare tree key let upperBoundLeqT compare (MapT tree) key = upperBoundLeq compare tree key -let upperBoundLeqTErr {~onError} compare (MapT tree) key = +let upperBoundLeqTErr compare (MapT tree) key = upperBoundLeqErr compare tree key pub let make {Key} (compare : Key -> Key -> [] Ordered) = Map { diff --git a/lib/Set.fram b/lib/Set.fram index 6988173c..738c3d8e 100644 --- a/lib/Set.fram +++ b/lib/Set.fram @@ -6,6 +6,8 @@ import open RedBlackTree (** Signature of Set *) +implicit ~onError + pub data Interval Value = Inclusion of Value | Exclusion of Value pub data Set Elem = Set of { @@ -128,7 +130,7 @@ let rec least tree = | Node {left} => least left end -let leastErr { ~onError } tree = +let leastErr tree = match least tree with | None => ~onError () | Some x => x @@ -141,7 +143,7 @@ let rec greatest tree = | Node {right} => greatest right end -let greatestErr { ~onError } tree = +let greatestErr tree = match greatest tree with | None => ~onError () | Some x => x @@ -293,7 +295,7 @@ let rec leastGt compare tree val = end end -let leastGtErr { ~onError } compare tree val = +let leastGtErr compare tree val = match leastGt compare tree val with | None => ~onError () | Some x => x @@ -314,7 +316,7 @@ let rec leastGeq compare tree val = end end -let leastGeqErr { ~onError } compare tree val = +let leastGeqErr compare tree val = match leastGeq compare tree val with | None => ~onError () | Some x => x @@ -335,7 +337,7 @@ let rec greatestLt compare tree val = end end -let greatestLtErr { ~onError } compare tree val = +let greatestLtErr compare tree val = match greatestLt compare tree val with | None => ~onError () | Some x => x @@ -356,7 +358,7 @@ let rec greatestLeq compare tree val = end end -let greatestLeqErr { ~onError } compare tree val = +let greatestLeqErr compare tree val = match greatestLeq compare tree val with | None => ~onError () | Some x => x From 9ade6494d323d21a2cf93957e9dca816d55617f6 Mon Sep 17 00:00:00 2001 From: Jakub Chomiczewski Date: Thu, 20 Feb 2025 14:34:02 +0100 Subject: [PATCH 19/27] Small changes --- .github/workflows/Test.yml | 0 .gitignore | 0 LICENSE | 0 README.md | 0 dune | 0 dune-project | 0 examples/LWT_lexical.fram | 0 examples/Modules/A.fram | 0 examples/Modules/B/A.fram | 0 examples/Modules/B/C/D.fram | 0 examples/Modules/C.fram | 0 examples/Modules/Main.fram | 0 examples/Prolog.fram | 0 examples/Pythagorean.fram | 0 examples/Tick.fram | 0 lib/Base/Assert.fram | 0 lib/Base/Bool.fram | 0 lib/Base/Char.fram | 0 lib/Base/Int.fram | 0 lib/Base/Int64.fram | 0 lib/Base/Operators.fram | 0 lib/Base/Option.fram | 0 lib/Base/String.fram | 0 lib/Base/Types.fram | 0 lib/List.fram | 0 lib/Map.fram | 30 ++--- lib/Prelude.fram | 9 -- lib/Queue.fram | 8 +- lib/RedBlackTree.fram | 21 ++-- lib/Set.fram | 111 ++++++++++++++++-- src/DblConfig.ml | 0 src/DblParser/Desugar.ml | 0 src/DblParser/Error.ml | 0 src/DblParser/Error.mli | 0 src/DblParser/File.ml | 0 src/DblParser/File.mli | 0 src/DblParser/Import.ml | 0 src/DblParser/Import.mli | 0 src/DblParser/Lexer.mli | 0 src/DblParser/Lexer.mll | 0 src/DblParser/Main.ml | 0 src/DblParser/Main.mli | 0 src/DblParser/Raw.ml | 0 src/DblParser/YaccParser.mly | 0 src/DblParser/dune | 0 src/Eval/Env.ml | 0 src/Eval/Env.mli | 0 src/Eval/Eval.ml | 0 src/Eval/Eval.mli | 0 src/Eval/External.ml | 0 src/Eval/Value.ml | 0 src/Eval/dune | 0 src/InterpLib/Error.ml | 0 src/InterpLib/Error.mli | 0 src/InterpLib/InternalError.ml | 0 src/InterpLib/InternalError.mli | 0 src/InterpLib/TextRangePrinting.ml | 0 src/InterpLib/TextRangePrinting.mli | 0 src/InterpLib/dune | 0 src/Lang/Core.ml | 0 src/Lang/Core.mli | 0 src/Lang/CorePriv/BuiltinType.ml | 0 src/Lang/CorePriv/Effect.ml | 0 src/Lang/CorePriv/Kind.ml | 0 src/Lang/CorePriv/SExprPrinter.ml | 0 src/Lang/CorePriv/Subst.ml | 0 src/Lang/CorePriv/Subst.mli | 0 src/Lang/CorePriv/Syntax.ml | 0 src/Lang/CorePriv/Type.ml | 0 src/Lang/CorePriv/TypeBase.ml | 0 src/Lang/CorePriv/WellTypedInvariant.ml | 0 src/Lang/CorePriv/dune | 0 src/Lang/Surface.ml | 0 src/Lang/Unif.ml | 0 src/Lang/Unif.mli | 0 src/Lang/UnifPriv/BuiltinType.ml | 0 src/Lang/UnifPriv/Effect.ml | 0 src/Lang/UnifPriv/KindBase.ml | 0 src/Lang/UnifPriv/KindBase.mli | 0 src/Lang/UnifPriv/Name.ml | 0 src/Lang/UnifPriv/Scope.ml | 0 src/Lang/UnifPriv/Scope.mli | 0 src/Lang/UnifPriv/Subst.ml | 0 src/Lang/UnifPriv/Subst.mli | 0 src/Lang/UnifPriv/TVar.ml | 0 src/Lang/UnifPriv/TVar.mli | 0 src/Lang/UnifPriv/Type.ml | 0 src/Lang/UnifPriv/TypeBase.ml | 0 src/Lang/UnifPriv/TypeBase.mli | 0 src/Lang/UnifPriv/TypeWhnf.ml | 0 src/Lang/UnifPriv/dune | 0 src/Lang/Untyped.ml | 0 src/Lang/dune | 0 src/Pipeline.ml | 0 src/Pipeline.mli | 0 src/ToCore/Common.ml | 0 src/ToCore/DataType.ml | 0 src/ToCore/DataType.mli | 0 src/ToCore/Env.ml | 0 src/ToCore/Env.mli | 0 src/ToCore/Error.ml | 0 src/ToCore/Error.mli | 0 src/ToCore/Main.ml | 0 src/ToCore/Main.mli | 0 src/ToCore/PatternContext.ml | 0 src/ToCore/PatternMatch.ml | 0 src/ToCore/PatternMatch.mli | 0 src/ToCore/Type.ml | 0 src/ToCore/dune | 0 src/TypeErase.ml | 0 src/TypeInference/Common.ml | 0 src/TypeInference/DataType.ml | 0 src/TypeInference/DataType.mli | 0 src/TypeInference/Def.ml | 0 src/TypeInference/Def.mli | 0 src/TypeInference/Env.ml | 0 src/TypeInference/Env.mli | 0 src/TypeInference/Error.ml | 0 src/TypeInference/Error.mli | 0 src/TypeInference/Expr.ml | 0 src/TypeInference/Expr.mli | 0 src/TypeInference/ExprUtils.ml | 0 src/TypeInference/ExprUtils.mli | 0 src/TypeInference/ImplicitEnv.ml | 0 src/TypeInference/ImplicitEnv.mli | 0 src/TypeInference/Main.ml | 0 src/TypeInference/Main.mli | 0 src/TypeInference/MatchClause.ml | 0 src/TypeInference/MatchClause.mli | 0 src/TypeInference/ModStack.ml | 0 src/TypeInference/ModStack.mli | 0 src/TypeInference/Module.ml | 0 src/TypeInference/Module.mli | 0 src/TypeInference/Name.ml | 0 src/TypeInference/Name.mli | 0 src/TypeInference/Pattern.ml | 0 src/TypeInference/Pattern.mli | 0 src/TypeInference/PolyExpr.ml | 0 src/TypeInference/PolyExpr.mli | 0 src/TypeInference/PreludeTypes.ml | 0 src/TypeInference/PreludeTypes.mli | 0 src/TypeInference/Pretty.ml | 0 src/TypeInference/Pretty.mli | 0 src/TypeInference/RecDefs.ml | 0 src/TypeInference/RecDefs.mli | 0 src/TypeInference/Type.ml | 0 src/TypeInference/Type.mli | 0 src/TypeInference/TypeCheckFix.ml | 0 src/TypeInference/TypeHints.ml | 0 src/TypeInference/TypeHints.mli | 0 src/TypeInference/TypeUtils.ml | 0 src/TypeInference/TypeUtils.mli | 0 src/TypeInference/Unification.ml | 0 src/TypeInference/Unification.mli | 0 src/TypeInference/Uniqueness.ml | 0 src/TypeInference/Uniqueness.mli | 0 src/TypeInference/dune | 0 src/Utils/BRef.ml | 0 src/Utils/BRef.mli | 0 src/Utils/Eq.ml | 0 src/Utils/Map1.ml | 0 src/Utils/Perm.ml | 0 src/Utils/Position.ml | 0 src/Utils/SExpr.ml | 0 src/Utils/SExpr.mli | 0 src/Utils/SyntaxNode.ml | 0 src/Utils/UID.ml | 0 src/Utils/UID.mli | 0 src/Utils/Var.ml | 0 src/Utils/Var.mli | 0 src/Utils/dune | 0 src/dbl.ml | 0 src/dune | 0 test/err/lexer_0000_illegalOp0.fram | 0 test/err/lexer_0001_illegalOp1.fram | 0 test/err/lexer_0002_eofInComment.fram | 0 test/err/parser_0000_illegalBinopPattern.fram | 0 test/err/parser_0001_illegalBinopCtor.fram | 0 test/err/parser_0002_illegalBinopMethod.fram | 0 test/err/tc_0000_implicitLoop.fram | 0 test/err/tc_0001_escapingType.fram | 0 test/err/tc_0002_escapingType.fram | 0 test/err/tc_0004_methodFn.fram | 0 test/err/tc_0005_specialBinops.fram | 0 test/err/tc_0006_unapplicableKind.fram | 0 test/err/tc_0007_missingOptionTypeDef.fram | 0 ...tc_0008_invalidOptionTypeConstructors.fram | 0 test/err/tc_0009_polymorphicOptionalArg.fram | 0 test/err/tc_0010_impureNonPositiveRecord.fram | 0 test/err/tc_0011_nonPositiveUVar.fram | 0 test/err/tc_0012_impureExprInPureMatch.fram | 0 test/ok/ok0000_emptyFile.fram | 0 test/ok/ok0001_id.fram | 0 test/ok/ok0002_poly.fram | 0 test/ok/ok0003_local.fram | 0 test/ok/ok0004_fnArg.fram | 0 test/ok/ok0005_let.fram | 0 test/ok/ok0006_fnArg.fram | 0 test/ok/ok0007_letArg.fram | 0 test/ok/ok0008_idHandler.fram | 0 test/ok/ok0009_purityRestriction.fram | 0 test/ok/ok0010_implicit.fram | 0 test/ok/ok0011_implicit.fram | 0 test/ok/ok0012_adt.fram | 0 test/ok/ok0013_emptyADT.fram | 0 test/ok/ok0014_arrows.fram | 0 test/ok/ok0015_ctor.fram | 0 test/ok/ok0016_trivialMatch.fram | 0 test/ok/ok0017_wildcard.fram | 0 test/ok/ok0018_namePattern.fram | 0 test/ok/ok0019_simplePattern.fram | 0 test/ok/ok0020_patternMatch.fram | 0 test/ok/ok0021_simpleMatch.fram | 0 test/ok/ok0022_deepMatch.fram | 0 test/ok/ok0023_letPattern.fram | 0 test/ok/ok0024_letFunc.fram | 0 test/ok/ok0025_letFuncImplicit.fram | 0 test/ok/ok0026_funSugar.fram | 0 test/ok/ok0027_explicitApp.fram | 0 test/ok/ok0028_patArg.fram | 0 test/ok/ok0029_handle.fram | 0 test/ok/ok0030_bt.fram | 0 test/ok/ok0031_explicitArg.fram | 0 test/ok/ok0032_dataArg.fram | 0 test/ok/ok0033_higherKinds.fram | 0 test/ok/ok0034_schemes.fram | 0 test/ok/ok0035_schemes.fram | 0 test/ok/ok0036_schemeAnnot.fram | 0 test/ok/ok0037_checkScheme.fram | 0 test/ok/ok0038_explicitArg.fram | 0 test/ok/ok0039_polymorphicImplicit.fram | 0 test/ok/ok0040_polymorphicFields.fram | 0 test/ok/ok0041_existentialTypes.fram | 0 test/ok/ok0042_existentialTypes.fram | 0 test/ok/ok0043_implicitCtorArgs.fram | 0 test/ok/ok0044_implicitCtorArgs.fram | 0 test/ok/ok0045_recursiveData.fram | 0 test/ok/ok0046_mutualDataRec.fram | 0 test/ok/ok0047_namedParam.fram | 0 test/ok/ok0048_explicitTypeInst.fram | 0 test/ok/ok0049_expilicitInstOrder.fram | 0 test/ok/ok0050_typeArgRename.fram | 0 test/ok/ok0051_existentialTypePattern.fram | 0 test/ok/ok0052_emptyMatch.fram | 0 test/ok/ok0053_firstClassHandler.fram | 0 test/ok/ok0054_firstClassHandler.fram | 0 test/ok/ok0055_complexHandlers.fram | 0 test/ok/ok0056_complexHandlers.fram | 0 test/ok/ok0057_dataArgLabels.fram | 0 test/ok/ok0058_unitState.fram | 0 test/ok/ok0059_effectArg.fram | 0 test/ok/ok0060_returnFinally.fram | 0 test/ok/ok0061_returnFinallyMatch.fram | 0 test/ok/ok0062_theLabel.fram | 0 test/ok/ok0064_typeAnnot.fram | 0 test/ok/ok0066_method.fram | 0 test/ok/ok0067_pureMethod.fram | 0 test/ok/ok0068_shadowCtors.fram | 0 test/ok/ok0069_effectCtorArg.fram | 0 test/ok/ok0070_effectMethodArg.fram | 0 test/ok/ok0071_numbers.fram | 0 test/ok/ok0072_strings.fram | 0 test/ok/ok0073_extern.fram | 0 test/ok/ok0074_implicitWithType.fram | 0 test/ok/ok0075_effectsFromImplicits.fram | 0 test/ok/ok0076_ifExpr.fram | 0 test/ok/ok0077_effectResume.fram | 0 test/ok/ok0078_unitMethods.fram | 0 test/ok/ok0079_impureMethod.fram | 0 test/ok/ok0080_moduleDef.fram | 0 test/ok/ok0081_nestedModule.fram | 0 test/ok/ok0082_moduleDataDef.fram | 0 test/ok/ok0083_pubPatternMatch.fram | 0 test/ok/ok0084_operators.fram | 0 test/ok/ok0085_letChecked.fram | 0 test/ok/ok0086_optionState.fram | 0 test/ok/ok0087_opratorOverloading.fram | 0 test/ok/ok0088_abstractData.fram | 0 test/ok/ok0089_pubPat.fram | 0 test/ok/ok0090_lists.fram | 0 test/ok/ok0091_namedParamMethod.fram | 0 test/ok/ok0092_multipleNamedMethodParams.fram | 0 test/ok/ok0093_specialBinops.fram | 0 test/ok/ok0094_unaryIf.fram | 0 test/ok/ok0095_wildcardTypeParam.fram | 0 test/ok/ok0096_fixTypeAnnot.fram | 0 test/ok/ok0097_recursion.fram | 0 test/ok/ok0098_mutualRecursion.fram | 0 test/ok/ok0099_nestedEffArrows.fram | 0 test/ok/ok0100_polymorphicRecursion.fram | 0 test/ok/ok0101_implicitParamsRecord.fram | 0 test/ok/ok0102_simpleRecord.fram | 0 test/ok/ok0103_genericRecords.fram | 0 test/ok/ok0104_chars.fram | 0 test/ok/ok0105_recFunWithNamedParam.fram | 0 test/ok/ok0106_recursiveMethod.fram | 0 test/ok/ok0107_polymorphicRecursion.fram | 0 test/ok/ok0108_modulePattern.fram | 0 test/ok/ok0109_fieldPattern.fram | 0 test/ok/ok0110_publicModulePattern.fram | 0 test/ok/ok0111_optionalParams.fram | 0 test/ok/ok0112_pureRecord.fram | 0 test/ok/ok0113_pureMatchingNonrecUVar.fram | 0 test/ok/ok0114_pureTail.fram | 0 test/ok/ok0115_purePatternMatching.fram | 0 test/ok/ok0116_pureRecordAccessor.fram | 0 test/ok/ok0117_comments.fram | 0 test/stdlib/stdlib0000_Int64.fram | 0 test/stdlib/stdlib0001_Map.fram | 81 ------------- test/stdlib/stdlib0001_Option.fram | 0 test/stdlib/stdlib0002_Map.fram | 88 ++++++++++++++ test/stdlib/stdlib0002_Set.fram | 72 ------------ test/stdlib/stdlib0003_Queue.fram | 22 ---- test/stdlib/stdlib0003_Set.fram | 76 ++++++++++++ test/stdlib/stdlib0004_Queue.fram | 24 ++++ test/test_suite | 0 316 files changed, 324 insertions(+), 218 deletions(-) mode change 100644 => 100755 .github/workflows/Test.yml mode change 100644 => 100755 .gitignore mode change 100644 => 100755 LICENSE mode change 100644 => 100755 README.md mode change 100644 => 100755 dune mode change 100644 => 100755 dune-project mode change 100644 => 100755 examples/LWT_lexical.fram mode change 100644 => 100755 examples/Modules/A.fram mode change 100644 => 100755 examples/Modules/B/A.fram mode change 100644 => 100755 examples/Modules/B/C/D.fram mode change 100644 => 100755 examples/Modules/C.fram mode change 100644 => 100755 examples/Modules/Main.fram mode change 100644 => 100755 examples/Prolog.fram mode change 100644 => 100755 examples/Pythagorean.fram mode change 100644 => 100755 examples/Tick.fram mode change 100644 => 100755 lib/Base/Assert.fram mode change 100644 => 100755 lib/Base/Bool.fram mode change 100644 => 100755 lib/Base/Char.fram mode change 100644 => 100755 lib/Base/Int.fram mode change 100644 => 100755 lib/Base/Int64.fram mode change 100644 => 100755 lib/Base/Operators.fram mode change 100644 => 100755 lib/Base/Option.fram mode change 100644 => 100755 lib/Base/String.fram mode change 100644 => 100755 lib/Base/Types.fram mode change 100644 => 100755 lib/List.fram mode change 100644 => 100755 lib/Map.fram mode change 100644 => 100755 lib/Prelude.fram mode change 100644 => 100755 lib/Queue.fram mode change 100644 => 100755 lib/RedBlackTree.fram mode change 100644 => 100755 lib/Set.fram mode change 100644 => 100755 src/DblConfig.ml mode change 100644 => 100755 src/DblParser/Desugar.ml mode change 100644 => 100755 src/DblParser/Error.ml mode change 100644 => 100755 src/DblParser/Error.mli mode change 100644 => 100755 src/DblParser/File.ml mode change 100644 => 100755 src/DblParser/File.mli mode change 100644 => 100755 src/DblParser/Import.ml mode change 100644 => 100755 src/DblParser/Import.mli mode change 100644 => 100755 src/DblParser/Lexer.mli mode change 100644 => 100755 src/DblParser/Lexer.mll mode change 100644 => 100755 src/DblParser/Main.ml mode change 100644 => 100755 src/DblParser/Main.mli mode change 100644 => 100755 src/DblParser/Raw.ml mode change 100644 => 100755 src/DblParser/YaccParser.mly mode change 100644 => 100755 src/DblParser/dune mode change 100644 => 100755 src/Eval/Env.ml mode change 100644 => 100755 src/Eval/Env.mli mode change 100644 => 100755 src/Eval/Eval.ml mode change 100644 => 100755 src/Eval/Eval.mli mode change 100644 => 100755 src/Eval/External.ml mode change 100644 => 100755 src/Eval/Value.ml mode change 100644 => 100755 src/Eval/dune mode change 100644 => 100755 src/InterpLib/Error.ml mode change 100644 => 100755 src/InterpLib/Error.mli mode change 100644 => 100755 src/InterpLib/InternalError.ml mode change 100644 => 100755 src/InterpLib/InternalError.mli mode change 100644 => 100755 src/InterpLib/TextRangePrinting.ml mode change 100644 => 100755 src/InterpLib/TextRangePrinting.mli mode change 100644 => 100755 src/InterpLib/dune mode change 100644 => 100755 src/Lang/Core.ml mode change 100644 => 100755 src/Lang/Core.mli mode change 100644 => 100755 src/Lang/CorePriv/BuiltinType.ml mode change 100644 => 100755 src/Lang/CorePriv/Effect.ml mode change 100644 => 100755 src/Lang/CorePriv/Kind.ml mode change 100644 => 100755 src/Lang/CorePriv/SExprPrinter.ml mode change 100644 => 100755 src/Lang/CorePriv/Subst.ml mode change 100644 => 100755 src/Lang/CorePriv/Subst.mli mode change 100644 => 100755 src/Lang/CorePriv/Syntax.ml mode change 100644 => 100755 src/Lang/CorePriv/Type.ml mode change 100644 => 100755 src/Lang/CorePriv/TypeBase.ml mode change 100644 => 100755 src/Lang/CorePriv/WellTypedInvariant.ml mode change 100644 => 100755 src/Lang/CorePriv/dune mode change 100644 => 100755 src/Lang/Surface.ml mode change 100644 => 100755 src/Lang/Unif.ml mode change 100644 => 100755 src/Lang/Unif.mli mode change 100644 => 100755 src/Lang/UnifPriv/BuiltinType.ml mode change 100644 => 100755 src/Lang/UnifPriv/Effect.ml mode change 100644 => 100755 src/Lang/UnifPriv/KindBase.ml mode change 100644 => 100755 src/Lang/UnifPriv/KindBase.mli mode change 100644 => 100755 src/Lang/UnifPriv/Name.ml mode change 100644 => 100755 src/Lang/UnifPriv/Scope.ml mode change 100644 => 100755 src/Lang/UnifPriv/Scope.mli mode change 100644 => 100755 src/Lang/UnifPriv/Subst.ml mode change 100644 => 100755 src/Lang/UnifPriv/Subst.mli mode change 100644 => 100755 src/Lang/UnifPriv/TVar.ml mode change 100644 => 100755 src/Lang/UnifPriv/TVar.mli mode change 100644 => 100755 src/Lang/UnifPriv/Type.ml mode change 100644 => 100755 src/Lang/UnifPriv/TypeBase.ml mode change 100644 => 100755 src/Lang/UnifPriv/TypeBase.mli mode change 100644 => 100755 src/Lang/UnifPriv/TypeWhnf.ml mode change 100644 => 100755 src/Lang/UnifPriv/dune mode change 100644 => 100755 src/Lang/Untyped.ml mode change 100644 => 100755 src/Lang/dune mode change 100644 => 100755 src/Pipeline.ml mode change 100644 => 100755 src/Pipeline.mli mode change 100644 => 100755 src/ToCore/Common.ml mode change 100644 => 100755 src/ToCore/DataType.ml mode change 100644 => 100755 src/ToCore/DataType.mli mode change 100644 => 100755 src/ToCore/Env.ml mode change 100644 => 100755 src/ToCore/Env.mli mode change 100644 => 100755 src/ToCore/Error.ml mode change 100644 => 100755 src/ToCore/Error.mli mode change 100644 => 100755 src/ToCore/Main.ml mode change 100644 => 100755 src/ToCore/Main.mli mode change 100644 => 100755 src/ToCore/PatternContext.ml mode change 100644 => 100755 src/ToCore/PatternMatch.ml mode change 100644 => 100755 src/ToCore/PatternMatch.mli mode change 100644 => 100755 src/ToCore/Type.ml mode change 100644 => 100755 src/ToCore/dune mode change 100644 => 100755 src/TypeErase.ml mode change 100644 => 100755 src/TypeInference/Common.ml mode change 100644 => 100755 src/TypeInference/DataType.ml mode change 100644 => 100755 src/TypeInference/DataType.mli mode change 100644 => 100755 src/TypeInference/Def.ml mode change 100644 => 100755 src/TypeInference/Def.mli mode change 100644 => 100755 src/TypeInference/Env.ml mode change 100644 => 100755 src/TypeInference/Env.mli mode change 100644 => 100755 src/TypeInference/Error.ml mode change 100644 => 100755 src/TypeInference/Error.mli mode change 100644 => 100755 src/TypeInference/Expr.ml mode change 100644 => 100755 src/TypeInference/Expr.mli mode change 100644 => 100755 src/TypeInference/ExprUtils.ml mode change 100644 => 100755 src/TypeInference/ExprUtils.mli mode change 100644 => 100755 src/TypeInference/ImplicitEnv.ml mode change 100644 => 100755 src/TypeInference/ImplicitEnv.mli mode change 100644 => 100755 src/TypeInference/Main.ml mode change 100644 => 100755 src/TypeInference/Main.mli mode change 100644 => 100755 src/TypeInference/MatchClause.ml mode change 100644 => 100755 src/TypeInference/MatchClause.mli mode change 100644 => 100755 src/TypeInference/ModStack.ml mode change 100644 => 100755 src/TypeInference/ModStack.mli mode change 100644 => 100755 src/TypeInference/Module.ml mode change 100644 => 100755 src/TypeInference/Module.mli mode change 100644 => 100755 src/TypeInference/Name.ml mode change 100644 => 100755 src/TypeInference/Name.mli mode change 100644 => 100755 src/TypeInference/Pattern.ml mode change 100644 => 100755 src/TypeInference/Pattern.mli mode change 100644 => 100755 src/TypeInference/PolyExpr.ml mode change 100644 => 100755 src/TypeInference/PolyExpr.mli mode change 100644 => 100755 src/TypeInference/PreludeTypes.ml mode change 100644 => 100755 src/TypeInference/PreludeTypes.mli mode change 100644 => 100755 src/TypeInference/Pretty.ml mode change 100644 => 100755 src/TypeInference/Pretty.mli mode change 100644 => 100755 src/TypeInference/RecDefs.ml mode change 100644 => 100755 src/TypeInference/RecDefs.mli mode change 100644 => 100755 src/TypeInference/Type.ml mode change 100644 => 100755 src/TypeInference/Type.mli mode change 100644 => 100755 src/TypeInference/TypeCheckFix.ml mode change 100644 => 100755 src/TypeInference/TypeHints.ml mode change 100644 => 100755 src/TypeInference/TypeHints.mli mode change 100644 => 100755 src/TypeInference/TypeUtils.ml mode change 100644 => 100755 src/TypeInference/TypeUtils.mli mode change 100644 => 100755 src/TypeInference/Unification.ml mode change 100644 => 100755 src/TypeInference/Unification.mli mode change 100644 => 100755 src/TypeInference/Uniqueness.ml mode change 100644 => 100755 src/TypeInference/Uniqueness.mli mode change 100644 => 100755 src/TypeInference/dune mode change 100644 => 100755 src/Utils/BRef.ml mode change 100644 => 100755 src/Utils/BRef.mli mode change 100644 => 100755 src/Utils/Eq.ml mode change 100644 => 100755 src/Utils/Map1.ml mode change 100644 => 100755 src/Utils/Perm.ml mode change 100644 => 100755 src/Utils/Position.ml mode change 100644 => 100755 src/Utils/SExpr.ml mode change 100644 => 100755 src/Utils/SExpr.mli mode change 100644 => 100755 src/Utils/SyntaxNode.ml mode change 100644 => 100755 src/Utils/UID.ml mode change 100644 => 100755 src/Utils/UID.mli mode change 100644 => 100755 src/Utils/Var.ml mode change 100644 => 100755 src/Utils/Var.mli mode change 100644 => 100755 src/Utils/dune mode change 100644 => 100755 src/dbl.ml mode change 100644 => 100755 src/dune mode change 100644 => 100755 test/err/lexer_0000_illegalOp0.fram mode change 100644 => 100755 test/err/lexer_0001_illegalOp1.fram mode change 100644 => 100755 test/err/lexer_0002_eofInComment.fram mode change 100644 => 100755 test/err/parser_0000_illegalBinopPattern.fram mode change 100644 => 100755 test/err/parser_0001_illegalBinopCtor.fram mode change 100644 => 100755 test/err/parser_0002_illegalBinopMethod.fram mode change 100644 => 100755 test/err/tc_0000_implicitLoop.fram mode change 100644 => 100755 test/err/tc_0001_escapingType.fram mode change 100644 => 100755 test/err/tc_0002_escapingType.fram mode change 100644 => 100755 test/err/tc_0004_methodFn.fram mode change 100644 => 100755 test/err/tc_0005_specialBinops.fram mode change 100644 => 100755 test/err/tc_0006_unapplicableKind.fram mode change 100644 => 100755 test/err/tc_0007_missingOptionTypeDef.fram mode change 100644 => 100755 test/err/tc_0008_invalidOptionTypeConstructors.fram mode change 100644 => 100755 test/err/tc_0009_polymorphicOptionalArg.fram mode change 100644 => 100755 test/err/tc_0010_impureNonPositiveRecord.fram mode change 100644 => 100755 test/err/tc_0011_nonPositiveUVar.fram mode change 100644 => 100755 test/err/tc_0012_impureExprInPureMatch.fram mode change 100644 => 100755 test/ok/ok0000_emptyFile.fram mode change 100644 => 100755 test/ok/ok0001_id.fram mode change 100644 => 100755 test/ok/ok0002_poly.fram mode change 100644 => 100755 test/ok/ok0003_local.fram mode change 100644 => 100755 test/ok/ok0004_fnArg.fram mode change 100644 => 100755 test/ok/ok0005_let.fram mode change 100644 => 100755 test/ok/ok0006_fnArg.fram mode change 100644 => 100755 test/ok/ok0007_letArg.fram mode change 100644 => 100755 test/ok/ok0008_idHandler.fram mode change 100644 => 100755 test/ok/ok0009_purityRestriction.fram mode change 100644 => 100755 test/ok/ok0010_implicit.fram mode change 100644 => 100755 test/ok/ok0011_implicit.fram mode change 100644 => 100755 test/ok/ok0012_adt.fram mode change 100644 => 100755 test/ok/ok0013_emptyADT.fram mode change 100644 => 100755 test/ok/ok0014_arrows.fram mode change 100644 => 100755 test/ok/ok0015_ctor.fram mode change 100644 => 100755 test/ok/ok0016_trivialMatch.fram mode change 100644 => 100755 test/ok/ok0017_wildcard.fram mode change 100644 => 100755 test/ok/ok0018_namePattern.fram mode change 100644 => 100755 test/ok/ok0019_simplePattern.fram mode change 100644 => 100755 test/ok/ok0020_patternMatch.fram mode change 100644 => 100755 test/ok/ok0021_simpleMatch.fram mode change 100644 => 100755 test/ok/ok0022_deepMatch.fram mode change 100644 => 100755 test/ok/ok0023_letPattern.fram mode change 100644 => 100755 test/ok/ok0024_letFunc.fram mode change 100644 => 100755 test/ok/ok0025_letFuncImplicit.fram mode change 100644 => 100755 test/ok/ok0026_funSugar.fram mode change 100644 => 100755 test/ok/ok0027_explicitApp.fram mode change 100644 => 100755 test/ok/ok0028_patArg.fram mode change 100644 => 100755 test/ok/ok0029_handle.fram mode change 100644 => 100755 test/ok/ok0030_bt.fram mode change 100644 => 100755 test/ok/ok0031_explicitArg.fram mode change 100644 => 100755 test/ok/ok0032_dataArg.fram mode change 100644 => 100755 test/ok/ok0033_higherKinds.fram mode change 100644 => 100755 test/ok/ok0034_schemes.fram mode change 100644 => 100755 test/ok/ok0035_schemes.fram mode change 100644 => 100755 test/ok/ok0036_schemeAnnot.fram mode change 100644 => 100755 test/ok/ok0037_checkScheme.fram mode change 100644 => 100755 test/ok/ok0038_explicitArg.fram mode change 100644 => 100755 test/ok/ok0039_polymorphicImplicit.fram mode change 100644 => 100755 test/ok/ok0040_polymorphicFields.fram mode change 100644 => 100755 test/ok/ok0041_existentialTypes.fram mode change 100644 => 100755 test/ok/ok0042_existentialTypes.fram mode change 100644 => 100755 test/ok/ok0043_implicitCtorArgs.fram mode change 100644 => 100755 test/ok/ok0044_implicitCtorArgs.fram mode change 100644 => 100755 test/ok/ok0045_recursiveData.fram mode change 100644 => 100755 test/ok/ok0046_mutualDataRec.fram mode change 100644 => 100755 test/ok/ok0047_namedParam.fram mode change 100644 => 100755 test/ok/ok0048_explicitTypeInst.fram mode change 100644 => 100755 test/ok/ok0049_expilicitInstOrder.fram mode change 100644 => 100755 test/ok/ok0050_typeArgRename.fram mode change 100644 => 100755 test/ok/ok0051_existentialTypePattern.fram mode change 100644 => 100755 test/ok/ok0052_emptyMatch.fram mode change 100644 => 100755 test/ok/ok0053_firstClassHandler.fram mode change 100644 => 100755 test/ok/ok0054_firstClassHandler.fram mode change 100644 => 100755 test/ok/ok0055_complexHandlers.fram mode change 100644 => 100755 test/ok/ok0056_complexHandlers.fram mode change 100644 => 100755 test/ok/ok0057_dataArgLabels.fram mode change 100644 => 100755 test/ok/ok0058_unitState.fram mode change 100644 => 100755 test/ok/ok0059_effectArg.fram mode change 100644 => 100755 test/ok/ok0060_returnFinally.fram mode change 100644 => 100755 test/ok/ok0061_returnFinallyMatch.fram mode change 100644 => 100755 test/ok/ok0062_theLabel.fram mode change 100644 => 100755 test/ok/ok0064_typeAnnot.fram mode change 100644 => 100755 test/ok/ok0066_method.fram mode change 100644 => 100755 test/ok/ok0067_pureMethod.fram mode change 100644 => 100755 test/ok/ok0068_shadowCtors.fram mode change 100644 => 100755 test/ok/ok0069_effectCtorArg.fram mode change 100644 => 100755 test/ok/ok0070_effectMethodArg.fram mode change 100644 => 100755 test/ok/ok0071_numbers.fram mode change 100644 => 100755 test/ok/ok0072_strings.fram mode change 100644 => 100755 test/ok/ok0073_extern.fram mode change 100644 => 100755 test/ok/ok0074_implicitWithType.fram mode change 100644 => 100755 test/ok/ok0075_effectsFromImplicits.fram mode change 100644 => 100755 test/ok/ok0076_ifExpr.fram mode change 100644 => 100755 test/ok/ok0077_effectResume.fram mode change 100644 => 100755 test/ok/ok0078_unitMethods.fram mode change 100644 => 100755 test/ok/ok0079_impureMethod.fram mode change 100644 => 100755 test/ok/ok0080_moduleDef.fram mode change 100644 => 100755 test/ok/ok0081_nestedModule.fram mode change 100644 => 100755 test/ok/ok0082_moduleDataDef.fram mode change 100644 => 100755 test/ok/ok0083_pubPatternMatch.fram mode change 100644 => 100755 test/ok/ok0084_operators.fram mode change 100644 => 100755 test/ok/ok0085_letChecked.fram mode change 100644 => 100755 test/ok/ok0086_optionState.fram mode change 100644 => 100755 test/ok/ok0087_opratorOverloading.fram mode change 100644 => 100755 test/ok/ok0088_abstractData.fram mode change 100644 => 100755 test/ok/ok0089_pubPat.fram mode change 100644 => 100755 test/ok/ok0090_lists.fram mode change 100644 => 100755 test/ok/ok0091_namedParamMethod.fram mode change 100644 => 100755 test/ok/ok0092_multipleNamedMethodParams.fram mode change 100644 => 100755 test/ok/ok0093_specialBinops.fram mode change 100644 => 100755 test/ok/ok0094_unaryIf.fram mode change 100644 => 100755 test/ok/ok0095_wildcardTypeParam.fram mode change 100644 => 100755 test/ok/ok0096_fixTypeAnnot.fram mode change 100644 => 100755 test/ok/ok0097_recursion.fram mode change 100644 => 100755 test/ok/ok0098_mutualRecursion.fram mode change 100644 => 100755 test/ok/ok0099_nestedEffArrows.fram mode change 100644 => 100755 test/ok/ok0100_polymorphicRecursion.fram mode change 100644 => 100755 test/ok/ok0101_implicitParamsRecord.fram mode change 100644 => 100755 test/ok/ok0102_simpleRecord.fram mode change 100644 => 100755 test/ok/ok0103_genericRecords.fram mode change 100644 => 100755 test/ok/ok0104_chars.fram mode change 100644 => 100755 test/ok/ok0105_recFunWithNamedParam.fram mode change 100644 => 100755 test/ok/ok0106_recursiveMethod.fram mode change 100644 => 100755 test/ok/ok0107_polymorphicRecursion.fram mode change 100644 => 100755 test/ok/ok0108_modulePattern.fram mode change 100644 => 100755 test/ok/ok0109_fieldPattern.fram mode change 100644 => 100755 test/ok/ok0110_publicModulePattern.fram mode change 100644 => 100755 test/ok/ok0111_optionalParams.fram mode change 100644 => 100755 test/ok/ok0112_pureRecord.fram mode change 100644 => 100755 test/ok/ok0113_pureMatchingNonrecUVar.fram mode change 100644 => 100755 test/ok/ok0114_pureTail.fram mode change 100644 => 100755 test/ok/ok0115_purePatternMatching.fram mode change 100644 => 100755 test/ok/ok0116_pureRecordAccessor.fram mode change 100644 => 100755 test/ok/ok0117_comments.fram mode change 100644 => 100755 test/stdlib/stdlib0000_Int64.fram delete mode 100644 test/stdlib/stdlib0001_Map.fram mode change 100644 => 100755 test/stdlib/stdlib0001_Option.fram create mode 100755 test/stdlib/stdlib0002_Map.fram delete mode 100644 test/stdlib/stdlib0002_Set.fram delete mode 100644 test/stdlib/stdlib0003_Queue.fram create mode 100755 test/stdlib/stdlib0003_Set.fram create mode 100755 test/stdlib/stdlib0004_Queue.fram mode change 100644 => 100755 test/test_suite diff --git a/.github/workflows/Test.yml b/.github/workflows/Test.yml old mode 100644 new mode 100755 diff --git a/.gitignore b/.gitignore old mode 100644 new mode 100755 diff --git a/LICENSE b/LICENSE old mode 100644 new mode 100755 diff --git a/README.md b/README.md old mode 100644 new mode 100755 diff --git a/dune b/dune old mode 100644 new mode 100755 diff --git a/dune-project b/dune-project old mode 100644 new mode 100755 diff --git a/examples/LWT_lexical.fram b/examples/LWT_lexical.fram old mode 100644 new mode 100755 diff --git a/examples/Modules/A.fram b/examples/Modules/A.fram old mode 100644 new mode 100755 diff --git a/examples/Modules/B/A.fram b/examples/Modules/B/A.fram old mode 100644 new mode 100755 diff --git a/examples/Modules/B/C/D.fram b/examples/Modules/B/C/D.fram old mode 100644 new mode 100755 diff --git a/examples/Modules/C.fram b/examples/Modules/C.fram old mode 100644 new mode 100755 diff --git a/examples/Modules/Main.fram b/examples/Modules/Main.fram old mode 100644 new mode 100755 diff --git a/examples/Prolog.fram b/examples/Prolog.fram old mode 100644 new mode 100755 diff --git a/examples/Pythagorean.fram b/examples/Pythagorean.fram old mode 100644 new mode 100755 diff --git a/examples/Tick.fram b/examples/Tick.fram old mode 100644 new mode 100755 diff --git a/lib/Base/Assert.fram b/lib/Base/Assert.fram old mode 100644 new mode 100755 diff --git a/lib/Base/Bool.fram b/lib/Base/Bool.fram old mode 100644 new mode 100755 diff --git a/lib/Base/Char.fram b/lib/Base/Char.fram old mode 100644 new mode 100755 diff --git a/lib/Base/Int.fram b/lib/Base/Int.fram old mode 100644 new mode 100755 diff --git a/lib/Base/Int64.fram b/lib/Base/Int64.fram old mode 100644 new mode 100755 diff --git a/lib/Base/Operators.fram b/lib/Base/Operators.fram old mode 100644 new mode 100755 diff --git a/lib/Base/Option.fram b/lib/Base/Option.fram old mode 100644 new mode 100755 diff --git a/lib/Base/String.fram b/lib/Base/String.fram old mode 100644 new mode 100755 diff --git a/lib/Base/Types.fram b/lib/Base/Types.fram old mode 100644 new mode 100755 diff --git a/lib/List.fram b/lib/List.fram old mode 100644 new mode 100755 diff --git a/lib/Map.fram b/lib/Map.fram old mode 100644 new mode 100755 index 4f6a93c5..d5eab927 --- a/lib/Map.fram +++ b/lib/Map.fram @@ -1,10 +1,12 @@ -(* This file is part of DBL, released under MIT license. - * See LICENSE for details. -*) +{# This file is part of DBL, released under MIT license. + # See LICENSE for details. + #} import open RedBlackTree -(** Signature *) +{# + # Signature + #} pub data Interval Value = Inclusion of Value | Exclusion of Value @@ -24,14 +26,14 @@ pub data Map Key = Map of { Key -> [] (Pair (T Val) Bool) , method member : {type Val} -> T Val -> Key -> [] Bool , method find : {type Val} -> T Val -> Key -> [] Option Val - (** @brief method that searches for an item and returns value - based on the search - @param key - @param absentf what value return if the element doesn't exist - @param presentf what value return if the element exist - @return tuple of found an item and it's value, - result of a given function absentf or presentf and orginal tree - *) + {# @brief method that searches for an item and returns value + # based on the search + # @param key + # @param absentf what value return if the element doesn't exist + # @param presentf what value return if the element exist + # @return tuple of found an item and it's value, + # result of a given function absentf or presentf and orginal tree + #} , method operate : {type Val,E} -> T Val -> Key -> (Unit -> [|E] Option Val) -> (Val -> [|E] Option Val) -> [|E] (Pair (Pair (Option Val) (Option Val)) (T Val)) @@ -88,7 +90,7 @@ pub data Map Key = Map of { T Val -> Key -> [Err] (Pair Key Val) } -(** implementation *) +# implementation let isEmpty tree = match tree with @@ -380,7 +382,7 @@ let range compare tree left right = data MapT Key Val = MapT of Tree (Pair Key Val) -// Wrappers +# Wrappers let isEmptyT (MapT tree) = isEmpty tree let insertT compare (MapT tree) key val = MapT (insert compare tree key val) diff --git a/lib/Prelude.fram b/lib/Prelude.fram old mode 100644 new mode 100755 index 1d5c6495..a41ab52f --- a/lib/Prelude.fram +++ b/lib/Prelude.fram @@ -47,16 +47,7 @@ pub module Int64 pub let ofInt (n : Int) = n.toInt64 end -pub let assert condition msg = - if condition then () else ((printStrLn msg) ; exit 1) - -pub data Comparable = Eq| Noteq - pub data Ordered = | Less | Equal | Greater - -pub let ordToComp elem = match elem with | Equal => Eq | _ => Noteq end - -pub method toComparable {self : Ordered} = ordToComp self diff --git a/lib/Queue.fram b/lib/Queue.fram old mode 100644 new mode 100755 index 6d41106e..df120021 --- a/lib/Queue.fram +++ b/lib/Queue.fram @@ -1,6 +1,6 @@ -(* This file is part of DBL, released under MIT license. - * See LICENSE for details. -*) +{# This file is part of DBL, released under MIT license. + # See LICENSE for details. + #} import List @@ -97,7 +97,7 @@ let head queue = match queue with | HMQueue Zero _ _ _ _ => None | HMQueue _ (x::xs) _ _ _ => Some x - | _ => None // Impossible + | _ => impossible () end let tail queue = diff --git a/lib/RedBlackTree.fram b/lib/RedBlackTree.fram old mode 100644 new mode 100755 index bb75005e..190fd4f3 --- a/lib/RedBlackTree.fram +++ b/lib/RedBlackTree.fram @@ -1,10 +1,17 @@ -(* This file is part of DBL, released under MIT license. - * See LICENSE for details. -*) +{# This file is part of DBL, released under MIT license. + # See LICENSE for details. + #} -import open Prelude +#import open Prelude +#import open Base/Assert import List +pub data Comparable = Eq| Noteq + +pub let ordToComp elem = match elem with | Equal => Eq | _ => Noteq end + +pub method toComparable {self : Ordered} = ordToComp self + data Color = | Red | Black @@ -182,10 +189,10 @@ pub let rec zipBlack tree zipper = zipBlack tree (Right Red right2 value1 :: Right Black left2 value2 :: rest) - //Impossible - | Left _ _ Leaf :: _ => tree + # Impossible + | Left _ _ Leaf :: _ => impossible () - | Right _ Leaf _ :: _ => tree + | Right _ Leaf _ :: _ => impossible () end diff --git a/lib/Set.fram b/lib/Set.fram old mode 100644 new mode 100755 index 738c3d8e..f4ef8481 --- a/lib/Set.fram +++ b/lib/Set.fram @@ -1,39 +1,124 @@ -(* This file is part of DBL, released under MIT license. - * See LICENSE for details. -*) +{# This file is part of DBL, released under MIT license. + # See LICENSE for details. + #} + import open RedBlackTree -(** Signature of Set *) +# Signature of Set implicit ~onError -pub data Interval Value = Inclusion of Value | Exclusion of Value +data Interval Value = Inclusion of Value | Exclusion of Value pub data Set Elem = Set of { T + {# @brief Creates empty set + #} , empty : T + {# @brief Method to testing whether given set is empty or not + # @return True if it's empty false otherwise + #} , method isEmpty : T -> [] Bool + {# @brief Method for inserting element to the set + # @param Element which will be inserted to the set + # @return Set with inserted value + #} , method insert : T -> Elem -> [] T + {# @brief Method for removig element from the set + # @param Element which will be removed + # @return Set with removed element + #} , method remove : T -> Elem -> [] T + {# @brief Method to test whether given element is in a given set or not + # @param Element which will be searched + # @return True if given element is in given set, false otherwise + #} , method member : T -> Elem -> [] Bool + {# @brief Method to fold left through structure of set + # @param Function that receives element and accumulator + # @param Accumulator + # @return Result of applying function on elements of set and accumulator + #} , method foldl : {type A,E} -> T -> (Elem -> A -> [|E] A) -> A -> [|E] A + {# @brief Method to fold right through structure of set + # @param Function that receives element and accumulator + # @param Accumulator + # @return Result of applying function on elements of set and accumulator + #} , method foldr : {type A,E} -> T -> (Elem -> A -> [|E] A) -> A -> [|E] A + {# @brief Method to convert set to list of elements + #} , method toList : T -> [] List Elem + {# @brief Method to create union of two sets + # @param Set + # @return Union of two sets + #} , method union : T -> T -> [] T + {# @brief Method to create intersection of two sets + # @param Set + # @return Intersection of two sets + #} , method intersection : T -> T -> [] T + {# @brief Method to create difference of two sets + # @param Set + # @return Difference of two sets + #} , method difference : T -> T -> [] T + {# @brief Method to check if two sets are equal + # @param Set + # @return True if two sets are equal, false otherwise. + #} , method eq : T -> T -> [] Bool + {# @brief Method to check if set which called this method is + # subset of a given set + # @param Set + # @return True if set is subset, false otherwise. + #} , method subset : T -> T -> [] Bool + {# @brief Split set to two sets one containing elements + # lesser then given element, second one containing equal or greater + # @param Elem + # @return Pair of sets with order and specification previously mentioned + #} , method partionLt : T -> Elem -> [] (Pair T T) + {# @brief Split set to two sets one containing elements + # lesser or equal then given element, second one containing greater + # @param Elem + # @return Pair of sets with order and specification previously mentioned + #} , method partionGt : T -> Elem -> [] (Pair T T) - , method range : T -> Interval Elem -> Interval Elem -> [] T + {# @brief Method that gives a subset in a given range + # @param First Bool - if the subset should include lower element or not + # @param First Elem - lower value which all elements + # in returned set will be greater (or equal) + # @param Second Bool - if the subset should include upper element or not + # @param Second Elem - upper value which all elements in + # in returned set will be lower (or equal) + # @return Subset in a given range + #} + , method range : T -> Bool -> Elem -> Bool -> Elem -> [] T + {# @brief Method that returns lowest stored value in a set + # @return Some value if the smallest element exist or otherwise None + #} , method lowerBound : T -> [] Option Elem + {# @brief Method that returns lowest stored value in a set + # @return smallest element or error + #} , method lowerBoundErr : {Err, ~onError : Unit -> [Err] Elem} -> T -> [Err] Elem + {# @brief Method that returns the greatest stored value in a set + # @return Some value if the greatest element exist or otherwise None + #} , method upperBound : T -> [] Option Elem + {# @brief Method that returns the greates stored value in a set + # @return greatest element or error + #} , method upperBoundErr : {Err, ~onError : Unit -> [Err] Elem} -> T -> [Err] Elem + {# + + #} , method lowerBoundGt : T -> Elem -> [] Option Elem , method lowerBoundGtErr : {Err, ~onError : Unit -> [Err] Elem} -> T -> Elem -> [Err] Elem @@ -48,7 +133,7 @@ pub data Set Elem = Set of { {Err, ~onError : Unit -> [Err] Elem} -> T -> Elem -> [Err] Elem } -(** Red black tree implementation *) +# Red black tree implementation data rec Q Val = Nil | E of Val , Q Val | T of Tree Val , Q Val @@ -242,10 +327,10 @@ let rec intersection compare tree1 tree2 = end end end - let rec difference compare tree1 tree2 = match tree1 with | Leaf => Leaf + | Node {left = left1, value = key1, right = right1} => match tree2 with | Leaf => tree1 @@ -264,7 +349,7 @@ let rec difference compare tree1 tree2 = let subset compare set1 set2 = subsetMain compare (T set1 Nil) (T set2 Nil) -let range compare tree left right = +let _range compare tree left right = match (left,right) with | (Inclusion left, Inclusion right) => let (_, tree') = partionLt compare tree left in @@ -279,6 +364,14 @@ let range compare tree left right = let (_, tree') = partionGt compare tree left in let (tree'',_) = partionLt compare tree' right in tree'' end + +let range compare tree incl left incr right = + match (incl,incr) with + | (False,False) => _range compare tree (Exclusion left) (Exclusion right) + | (False,True) => _range compare tree (Exclusion left) (Inclusion right) + | (True,False) => _range compare tree (Inclusion left) (Exclusion right) + | (True,True) => _range compare tree (Inclusion left) (Inclusion right) + end let rec leastGt compare tree val = match tree with diff --git a/src/DblConfig.ml b/src/DblConfig.ml old mode 100644 new mode 100755 diff --git a/src/DblParser/Desugar.ml b/src/DblParser/Desugar.ml old mode 100644 new mode 100755 diff --git a/src/DblParser/Error.ml b/src/DblParser/Error.ml old mode 100644 new mode 100755 diff --git a/src/DblParser/Error.mli b/src/DblParser/Error.mli old mode 100644 new mode 100755 diff --git a/src/DblParser/File.ml b/src/DblParser/File.ml old mode 100644 new mode 100755 diff --git a/src/DblParser/File.mli b/src/DblParser/File.mli old mode 100644 new mode 100755 diff --git a/src/DblParser/Import.ml b/src/DblParser/Import.ml old mode 100644 new mode 100755 diff --git a/src/DblParser/Import.mli b/src/DblParser/Import.mli old mode 100644 new mode 100755 diff --git a/src/DblParser/Lexer.mli b/src/DblParser/Lexer.mli old mode 100644 new mode 100755 diff --git a/src/DblParser/Lexer.mll b/src/DblParser/Lexer.mll old mode 100644 new mode 100755 diff --git a/src/DblParser/Main.ml b/src/DblParser/Main.ml old mode 100644 new mode 100755 diff --git a/src/DblParser/Main.mli b/src/DblParser/Main.mli old mode 100644 new mode 100755 diff --git a/src/DblParser/Raw.ml b/src/DblParser/Raw.ml old mode 100644 new mode 100755 diff --git a/src/DblParser/YaccParser.mly b/src/DblParser/YaccParser.mly old mode 100644 new mode 100755 diff --git a/src/DblParser/dune b/src/DblParser/dune old mode 100644 new mode 100755 diff --git a/src/Eval/Env.ml b/src/Eval/Env.ml old mode 100644 new mode 100755 diff --git a/src/Eval/Env.mli b/src/Eval/Env.mli old mode 100644 new mode 100755 diff --git a/src/Eval/Eval.ml b/src/Eval/Eval.ml old mode 100644 new mode 100755 diff --git a/src/Eval/Eval.mli b/src/Eval/Eval.mli old mode 100644 new mode 100755 diff --git a/src/Eval/External.ml b/src/Eval/External.ml old mode 100644 new mode 100755 diff --git a/src/Eval/Value.ml b/src/Eval/Value.ml old mode 100644 new mode 100755 diff --git a/src/Eval/dune b/src/Eval/dune old mode 100644 new mode 100755 diff --git a/src/InterpLib/Error.ml b/src/InterpLib/Error.ml old mode 100644 new mode 100755 diff --git a/src/InterpLib/Error.mli b/src/InterpLib/Error.mli old mode 100644 new mode 100755 diff --git a/src/InterpLib/InternalError.ml b/src/InterpLib/InternalError.ml old mode 100644 new mode 100755 diff --git a/src/InterpLib/InternalError.mli b/src/InterpLib/InternalError.mli old mode 100644 new mode 100755 diff --git a/src/InterpLib/TextRangePrinting.ml b/src/InterpLib/TextRangePrinting.ml old mode 100644 new mode 100755 diff --git a/src/InterpLib/TextRangePrinting.mli b/src/InterpLib/TextRangePrinting.mli old mode 100644 new mode 100755 diff --git a/src/InterpLib/dune b/src/InterpLib/dune old mode 100644 new mode 100755 diff --git a/src/Lang/Core.ml b/src/Lang/Core.ml old mode 100644 new mode 100755 diff --git a/src/Lang/Core.mli b/src/Lang/Core.mli old mode 100644 new mode 100755 diff --git a/src/Lang/CorePriv/BuiltinType.ml b/src/Lang/CorePriv/BuiltinType.ml old mode 100644 new mode 100755 diff --git a/src/Lang/CorePriv/Effect.ml b/src/Lang/CorePriv/Effect.ml old mode 100644 new mode 100755 diff --git a/src/Lang/CorePriv/Kind.ml b/src/Lang/CorePriv/Kind.ml old mode 100644 new mode 100755 diff --git a/src/Lang/CorePriv/SExprPrinter.ml b/src/Lang/CorePriv/SExprPrinter.ml old mode 100644 new mode 100755 diff --git a/src/Lang/CorePriv/Subst.ml b/src/Lang/CorePriv/Subst.ml old mode 100644 new mode 100755 diff --git a/src/Lang/CorePriv/Subst.mli b/src/Lang/CorePriv/Subst.mli old mode 100644 new mode 100755 diff --git a/src/Lang/CorePriv/Syntax.ml b/src/Lang/CorePriv/Syntax.ml old mode 100644 new mode 100755 diff --git a/src/Lang/CorePriv/Type.ml b/src/Lang/CorePriv/Type.ml old mode 100644 new mode 100755 diff --git a/src/Lang/CorePriv/TypeBase.ml b/src/Lang/CorePriv/TypeBase.ml old mode 100644 new mode 100755 diff --git a/src/Lang/CorePriv/WellTypedInvariant.ml b/src/Lang/CorePriv/WellTypedInvariant.ml old mode 100644 new mode 100755 diff --git a/src/Lang/CorePriv/dune b/src/Lang/CorePriv/dune old mode 100644 new mode 100755 diff --git a/src/Lang/Surface.ml b/src/Lang/Surface.ml old mode 100644 new mode 100755 diff --git a/src/Lang/Unif.ml b/src/Lang/Unif.ml old mode 100644 new mode 100755 diff --git a/src/Lang/Unif.mli b/src/Lang/Unif.mli old mode 100644 new mode 100755 diff --git a/src/Lang/UnifPriv/BuiltinType.ml b/src/Lang/UnifPriv/BuiltinType.ml old mode 100644 new mode 100755 diff --git a/src/Lang/UnifPriv/Effect.ml b/src/Lang/UnifPriv/Effect.ml old mode 100644 new mode 100755 diff --git a/src/Lang/UnifPriv/KindBase.ml b/src/Lang/UnifPriv/KindBase.ml old mode 100644 new mode 100755 diff --git a/src/Lang/UnifPriv/KindBase.mli b/src/Lang/UnifPriv/KindBase.mli old mode 100644 new mode 100755 diff --git a/src/Lang/UnifPriv/Name.ml b/src/Lang/UnifPriv/Name.ml old mode 100644 new mode 100755 diff --git a/src/Lang/UnifPriv/Scope.ml b/src/Lang/UnifPriv/Scope.ml old mode 100644 new mode 100755 diff --git a/src/Lang/UnifPriv/Scope.mli b/src/Lang/UnifPriv/Scope.mli old mode 100644 new mode 100755 diff --git a/src/Lang/UnifPriv/Subst.ml b/src/Lang/UnifPriv/Subst.ml old mode 100644 new mode 100755 diff --git a/src/Lang/UnifPriv/Subst.mli b/src/Lang/UnifPriv/Subst.mli old mode 100644 new mode 100755 diff --git a/src/Lang/UnifPriv/TVar.ml b/src/Lang/UnifPriv/TVar.ml old mode 100644 new mode 100755 diff --git a/src/Lang/UnifPriv/TVar.mli b/src/Lang/UnifPriv/TVar.mli old mode 100644 new mode 100755 diff --git a/src/Lang/UnifPriv/Type.ml b/src/Lang/UnifPriv/Type.ml old mode 100644 new mode 100755 diff --git a/src/Lang/UnifPriv/TypeBase.ml b/src/Lang/UnifPriv/TypeBase.ml old mode 100644 new mode 100755 diff --git a/src/Lang/UnifPriv/TypeBase.mli b/src/Lang/UnifPriv/TypeBase.mli old mode 100644 new mode 100755 diff --git a/src/Lang/UnifPriv/TypeWhnf.ml b/src/Lang/UnifPriv/TypeWhnf.ml old mode 100644 new mode 100755 diff --git a/src/Lang/UnifPriv/dune b/src/Lang/UnifPriv/dune old mode 100644 new mode 100755 diff --git a/src/Lang/Untyped.ml b/src/Lang/Untyped.ml old mode 100644 new mode 100755 diff --git a/src/Lang/dune b/src/Lang/dune old mode 100644 new mode 100755 diff --git a/src/Pipeline.ml b/src/Pipeline.ml old mode 100644 new mode 100755 diff --git a/src/Pipeline.mli b/src/Pipeline.mli old mode 100644 new mode 100755 diff --git a/src/ToCore/Common.ml b/src/ToCore/Common.ml old mode 100644 new mode 100755 diff --git a/src/ToCore/DataType.ml b/src/ToCore/DataType.ml old mode 100644 new mode 100755 diff --git a/src/ToCore/DataType.mli b/src/ToCore/DataType.mli old mode 100644 new mode 100755 diff --git a/src/ToCore/Env.ml b/src/ToCore/Env.ml old mode 100644 new mode 100755 diff --git a/src/ToCore/Env.mli b/src/ToCore/Env.mli old mode 100644 new mode 100755 diff --git a/src/ToCore/Error.ml b/src/ToCore/Error.ml old mode 100644 new mode 100755 diff --git a/src/ToCore/Error.mli b/src/ToCore/Error.mli old mode 100644 new mode 100755 diff --git a/src/ToCore/Main.ml b/src/ToCore/Main.ml old mode 100644 new mode 100755 diff --git a/src/ToCore/Main.mli b/src/ToCore/Main.mli old mode 100644 new mode 100755 diff --git a/src/ToCore/PatternContext.ml b/src/ToCore/PatternContext.ml old mode 100644 new mode 100755 diff --git a/src/ToCore/PatternMatch.ml b/src/ToCore/PatternMatch.ml old mode 100644 new mode 100755 diff --git a/src/ToCore/PatternMatch.mli b/src/ToCore/PatternMatch.mli old mode 100644 new mode 100755 diff --git a/src/ToCore/Type.ml b/src/ToCore/Type.ml old mode 100644 new mode 100755 diff --git a/src/ToCore/dune b/src/ToCore/dune old mode 100644 new mode 100755 diff --git a/src/TypeErase.ml b/src/TypeErase.ml old mode 100644 new mode 100755 diff --git a/src/TypeInference/Common.ml b/src/TypeInference/Common.ml old mode 100644 new mode 100755 diff --git a/src/TypeInference/DataType.ml b/src/TypeInference/DataType.ml old mode 100644 new mode 100755 diff --git a/src/TypeInference/DataType.mli b/src/TypeInference/DataType.mli old mode 100644 new mode 100755 diff --git a/src/TypeInference/Def.ml b/src/TypeInference/Def.ml old mode 100644 new mode 100755 diff --git a/src/TypeInference/Def.mli b/src/TypeInference/Def.mli old mode 100644 new mode 100755 diff --git a/src/TypeInference/Env.ml b/src/TypeInference/Env.ml old mode 100644 new mode 100755 diff --git a/src/TypeInference/Env.mli b/src/TypeInference/Env.mli old mode 100644 new mode 100755 diff --git a/src/TypeInference/Error.ml b/src/TypeInference/Error.ml old mode 100644 new mode 100755 diff --git a/src/TypeInference/Error.mli b/src/TypeInference/Error.mli old mode 100644 new mode 100755 diff --git a/src/TypeInference/Expr.ml b/src/TypeInference/Expr.ml old mode 100644 new mode 100755 diff --git a/src/TypeInference/Expr.mli b/src/TypeInference/Expr.mli old mode 100644 new mode 100755 diff --git a/src/TypeInference/ExprUtils.ml b/src/TypeInference/ExprUtils.ml old mode 100644 new mode 100755 diff --git a/src/TypeInference/ExprUtils.mli b/src/TypeInference/ExprUtils.mli old mode 100644 new mode 100755 diff --git a/src/TypeInference/ImplicitEnv.ml b/src/TypeInference/ImplicitEnv.ml old mode 100644 new mode 100755 diff --git a/src/TypeInference/ImplicitEnv.mli b/src/TypeInference/ImplicitEnv.mli old mode 100644 new mode 100755 diff --git a/src/TypeInference/Main.ml b/src/TypeInference/Main.ml old mode 100644 new mode 100755 diff --git a/src/TypeInference/Main.mli b/src/TypeInference/Main.mli old mode 100644 new mode 100755 diff --git a/src/TypeInference/MatchClause.ml b/src/TypeInference/MatchClause.ml old mode 100644 new mode 100755 diff --git a/src/TypeInference/MatchClause.mli b/src/TypeInference/MatchClause.mli old mode 100644 new mode 100755 diff --git a/src/TypeInference/ModStack.ml b/src/TypeInference/ModStack.ml old mode 100644 new mode 100755 diff --git a/src/TypeInference/ModStack.mli b/src/TypeInference/ModStack.mli old mode 100644 new mode 100755 diff --git a/src/TypeInference/Module.ml b/src/TypeInference/Module.ml old mode 100644 new mode 100755 diff --git a/src/TypeInference/Module.mli b/src/TypeInference/Module.mli old mode 100644 new mode 100755 diff --git a/src/TypeInference/Name.ml b/src/TypeInference/Name.ml old mode 100644 new mode 100755 diff --git a/src/TypeInference/Name.mli b/src/TypeInference/Name.mli old mode 100644 new mode 100755 diff --git a/src/TypeInference/Pattern.ml b/src/TypeInference/Pattern.ml old mode 100644 new mode 100755 diff --git a/src/TypeInference/Pattern.mli b/src/TypeInference/Pattern.mli old mode 100644 new mode 100755 diff --git a/src/TypeInference/PolyExpr.ml b/src/TypeInference/PolyExpr.ml old mode 100644 new mode 100755 diff --git a/src/TypeInference/PolyExpr.mli b/src/TypeInference/PolyExpr.mli old mode 100644 new mode 100755 diff --git a/src/TypeInference/PreludeTypes.ml b/src/TypeInference/PreludeTypes.ml old mode 100644 new mode 100755 diff --git a/src/TypeInference/PreludeTypes.mli b/src/TypeInference/PreludeTypes.mli old mode 100644 new mode 100755 diff --git a/src/TypeInference/Pretty.ml b/src/TypeInference/Pretty.ml old mode 100644 new mode 100755 diff --git a/src/TypeInference/Pretty.mli b/src/TypeInference/Pretty.mli old mode 100644 new mode 100755 diff --git a/src/TypeInference/RecDefs.ml b/src/TypeInference/RecDefs.ml old mode 100644 new mode 100755 diff --git a/src/TypeInference/RecDefs.mli b/src/TypeInference/RecDefs.mli old mode 100644 new mode 100755 diff --git a/src/TypeInference/Type.ml b/src/TypeInference/Type.ml old mode 100644 new mode 100755 diff --git a/src/TypeInference/Type.mli b/src/TypeInference/Type.mli old mode 100644 new mode 100755 diff --git a/src/TypeInference/TypeCheckFix.ml b/src/TypeInference/TypeCheckFix.ml old mode 100644 new mode 100755 diff --git a/src/TypeInference/TypeHints.ml b/src/TypeInference/TypeHints.ml old mode 100644 new mode 100755 diff --git a/src/TypeInference/TypeHints.mli b/src/TypeInference/TypeHints.mli old mode 100644 new mode 100755 diff --git a/src/TypeInference/TypeUtils.ml b/src/TypeInference/TypeUtils.ml old mode 100644 new mode 100755 diff --git a/src/TypeInference/TypeUtils.mli b/src/TypeInference/TypeUtils.mli old mode 100644 new mode 100755 diff --git a/src/TypeInference/Unification.ml b/src/TypeInference/Unification.ml old mode 100644 new mode 100755 diff --git a/src/TypeInference/Unification.mli b/src/TypeInference/Unification.mli old mode 100644 new mode 100755 diff --git a/src/TypeInference/Uniqueness.ml b/src/TypeInference/Uniqueness.ml old mode 100644 new mode 100755 diff --git a/src/TypeInference/Uniqueness.mli b/src/TypeInference/Uniqueness.mli old mode 100644 new mode 100755 diff --git a/src/TypeInference/dune b/src/TypeInference/dune old mode 100644 new mode 100755 diff --git a/src/Utils/BRef.ml b/src/Utils/BRef.ml old mode 100644 new mode 100755 diff --git a/src/Utils/BRef.mli b/src/Utils/BRef.mli old mode 100644 new mode 100755 diff --git a/src/Utils/Eq.ml b/src/Utils/Eq.ml old mode 100644 new mode 100755 diff --git a/src/Utils/Map1.ml b/src/Utils/Map1.ml old mode 100644 new mode 100755 diff --git a/src/Utils/Perm.ml b/src/Utils/Perm.ml old mode 100644 new mode 100755 diff --git a/src/Utils/Position.ml b/src/Utils/Position.ml old mode 100644 new mode 100755 diff --git a/src/Utils/SExpr.ml b/src/Utils/SExpr.ml old mode 100644 new mode 100755 diff --git a/src/Utils/SExpr.mli b/src/Utils/SExpr.mli old mode 100644 new mode 100755 diff --git a/src/Utils/SyntaxNode.ml b/src/Utils/SyntaxNode.ml old mode 100644 new mode 100755 diff --git a/src/Utils/UID.ml b/src/Utils/UID.ml old mode 100644 new mode 100755 diff --git a/src/Utils/UID.mli b/src/Utils/UID.mli old mode 100644 new mode 100755 diff --git a/src/Utils/Var.ml b/src/Utils/Var.ml old mode 100644 new mode 100755 diff --git a/src/Utils/Var.mli b/src/Utils/Var.mli old mode 100644 new mode 100755 diff --git a/src/Utils/dune b/src/Utils/dune old mode 100644 new mode 100755 diff --git a/src/dbl.ml b/src/dbl.ml old mode 100644 new mode 100755 diff --git a/src/dune b/src/dune old mode 100644 new mode 100755 diff --git a/test/err/lexer_0000_illegalOp0.fram b/test/err/lexer_0000_illegalOp0.fram old mode 100644 new mode 100755 diff --git a/test/err/lexer_0001_illegalOp1.fram b/test/err/lexer_0001_illegalOp1.fram old mode 100644 new mode 100755 diff --git a/test/err/lexer_0002_eofInComment.fram b/test/err/lexer_0002_eofInComment.fram old mode 100644 new mode 100755 diff --git a/test/err/parser_0000_illegalBinopPattern.fram b/test/err/parser_0000_illegalBinopPattern.fram old mode 100644 new mode 100755 diff --git a/test/err/parser_0001_illegalBinopCtor.fram b/test/err/parser_0001_illegalBinopCtor.fram old mode 100644 new mode 100755 diff --git a/test/err/parser_0002_illegalBinopMethod.fram b/test/err/parser_0002_illegalBinopMethod.fram old mode 100644 new mode 100755 diff --git a/test/err/tc_0000_implicitLoop.fram b/test/err/tc_0000_implicitLoop.fram old mode 100644 new mode 100755 diff --git a/test/err/tc_0001_escapingType.fram b/test/err/tc_0001_escapingType.fram old mode 100644 new mode 100755 diff --git a/test/err/tc_0002_escapingType.fram b/test/err/tc_0002_escapingType.fram old mode 100644 new mode 100755 diff --git a/test/err/tc_0004_methodFn.fram b/test/err/tc_0004_methodFn.fram old mode 100644 new mode 100755 diff --git a/test/err/tc_0005_specialBinops.fram b/test/err/tc_0005_specialBinops.fram old mode 100644 new mode 100755 diff --git a/test/err/tc_0006_unapplicableKind.fram b/test/err/tc_0006_unapplicableKind.fram old mode 100644 new mode 100755 diff --git a/test/err/tc_0007_missingOptionTypeDef.fram b/test/err/tc_0007_missingOptionTypeDef.fram old mode 100644 new mode 100755 diff --git a/test/err/tc_0008_invalidOptionTypeConstructors.fram b/test/err/tc_0008_invalidOptionTypeConstructors.fram old mode 100644 new mode 100755 diff --git a/test/err/tc_0009_polymorphicOptionalArg.fram b/test/err/tc_0009_polymorphicOptionalArg.fram old mode 100644 new mode 100755 diff --git a/test/err/tc_0010_impureNonPositiveRecord.fram b/test/err/tc_0010_impureNonPositiveRecord.fram old mode 100644 new mode 100755 diff --git a/test/err/tc_0011_nonPositiveUVar.fram b/test/err/tc_0011_nonPositiveUVar.fram old mode 100644 new mode 100755 diff --git a/test/err/tc_0012_impureExprInPureMatch.fram b/test/err/tc_0012_impureExprInPureMatch.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0000_emptyFile.fram b/test/ok/ok0000_emptyFile.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0001_id.fram b/test/ok/ok0001_id.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0002_poly.fram b/test/ok/ok0002_poly.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0003_local.fram b/test/ok/ok0003_local.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0004_fnArg.fram b/test/ok/ok0004_fnArg.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0005_let.fram b/test/ok/ok0005_let.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0006_fnArg.fram b/test/ok/ok0006_fnArg.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0007_letArg.fram b/test/ok/ok0007_letArg.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0008_idHandler.fram b/test/ok/ok0008_idHandler.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0009_purityRestriction.fram b/test/ok/ok0009_purityRestriction.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0010_implicit.fram b/test/ok/ok0010_implicit.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0011_implicit.fram b/test/ok/ok0011_implicit.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0012_adt.fram b/test/ok/ok0012_adt.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0013_emptyADT.fram b/test/ok/ok0013_emptyADT.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0014_arrows.fram b/test/ok/ok0014_arrows.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0015_ctor.fram b/test/ok/ok0015_ctor.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0016_trivialMatch.fram b/test/ok/ok0016_trivialMatch.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0017_wildcard.fram b/test/ok/ok0017_wildcard.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0018_namePattern.fram b/test/ok/ok0018_namePattern.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0019_simplePattern.fram b/test/ok/ok0019_simplePattern.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0020_patternMatch.fram b/test/ok/ok0020_patternMatch.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0021_simpleMatch.fram b/test/ok/ok0021_simpleMatch.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0022_deepMatch.fram b/test/ok/ok0022_deepMatch.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0023_letPattern.fram b/test/ok/ok0023_letPattern.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0024_letFunc.fram b/test/ok/ok0024_letFunc.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0025_letFuncImplicit.fram b/test/ok/ok0025_letFuncImplicit.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0026_funSugar.fram b/test/ok/ok0026_funSugar.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0027_explicitApp.fram b/test/ok/ok0027_explicitApp.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0028_patArg.fram b/test/ok/ok0028_patArg.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0029_handle.fram b/test/ok/ok0029_handle.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0030_bt.fram b/test/ok/ok0030_bt.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0031_explicitArg.fram b/test/ok/ok0031_explicitArg.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0032_dataArg.fram b/test/ok/ok0032_dataArg.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0033_higherKinds.fram b/test/ok/ok0033_higherKinds.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0034_schemes.fram b/test/ok/ok0034_schemes.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0035_schemes.fram b/test/ok/ok0035_schemes.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0036_schemeAnnot.fram b/test/ok/ok0036_schemeAnnot.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0037_checkScheme.fram b/test/ok/ok0037_checkScheme.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0038_explicitArg.fram b/test/ok/ok0038_explicitArg.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0039_polymorphicImplicit.fram b/test/ok/ok0039_polymorphicImplicit.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0040_polymorphicFields.fram b/test/ok/ok0040_polymorphicFields.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0041_existentialTypes.fram b/test/ok/ok0041_existentialTypes.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0042_existentialTypes.fram b/test/ok/ok0042_existentialTypes.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0043_implicitCtorArgs.fram b/test/ok/ok0043_implicitCtorArgs.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0044_implicitCtorArgs.fram b/test/ok/ok0044_implicitCtorArgs.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0045_recursiveData.fram b/test/ok/ok0045_recursiveData.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0046_mutualDataRec.fram b/test/ok/ok0046_mutualDataRec.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0047_namedParam.fram b/test/ok/ok0047_namedParam.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0048_explicitTypeInst.fram b/test/ok/ok0048_explicitTypeInst.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0049_expilicitInstOrder.fram b/test/ok/ok0049_expilicitInstOrder.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0050_typeArgRename.fram b/test/ok/ok0050_typeArgRename.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0051_existentialTypePattern.fram b/test/ok/ok0051_existentialTypePattern.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0052_emptyMatch.fram b/test/ok/ok0052_emptyMatch.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0053_firstClassHandler.fram b/test/ok/ok0053_firstClassHandler.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0054_firstClassHandler.fram b/test/ok/ok0054_firstClassHandler.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0055_complexHandlers.fram b/test/ok/ok0055_complexHandlers.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0056_complexHandlers.fram b/test/ok/ok0056_complexHandlers.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0057_dataArgLabels.fram b/test/ok/ok0057_dataArgLabels.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0058_unitState.fram b/test/ok/ok0058_unitState.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0059_effectArg.fram b/test/ok/ok0059_effectArg.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0060_returnFinally.fram b/test/ok/ok0060_returnFinally.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0061_returnFinallyMatch.fram b/test/ok/ok0061_returnFinallyMatch.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0062_theLabel.fram b/test/ok/ok0062_theLabel.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0064_typeAnnot.fram b/test/ok/ok0064_typeAnnot.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0066_method.fram b/test/ok/ok0066_method.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0067_pureMethod.fram b/test/ok/ok0067_pureMethod.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0068_shadowCtors.fram b/test/ok/ok0068_shadowCtors.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0069_effectCtorArg.fram b/test/ok/ok0069_effectCtorArg.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0070_effectMethodArg.fram b/test/ok/ok0070_effectMethodArg.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0071_numbers.fram b/test/ok/ok0071_numbers.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0072_strings.fram b/test/ok/ok0072_strings.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0073_extern.fram b/test/ok/ok0073_extern.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0074_implicitWithType.fram b/test/ok/ok0074_implicitWithType.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0075_effectsFromImplicits.fram b/test/ok/ok0075_effectsFromImplicits.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0076_ifExpr.fram b/test/ok/ok0076_ifExpr.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0077_effectResume.fram b/test/ok/ok0077_effectResume.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0078_unitMethods.fram b/test/ok/ok0078_unitMethods.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0079_impureMethod.fram b/test/ok/ok0079_impureMethod.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0080_moduleDef.fram b/test/ok/ok0080_moduleDef.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0081_nestedModule.fram b/test/ok/ok0081_nestedModule.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0082_moduleDataDef.fram b/test/ok/ok0082_moduleDataDef.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0083_pubPatternMatch.fram b/test/ok/ok0083_pubPatternMatch.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0084_operators.fram b/test/ok/ok0084_operators.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0085_letChecked.fram b/test/ok/ok0085_letChecked.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0086_optionState.fram b/test/ok/ok0086_optionState.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0087_opratorOverloading.fram b/test/ok/ok0087_opratorOverloading.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0088_abstractData.fram b/test/ok/ok0088_abstractData.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0089_pubPat.fram b/test/ok/ok0089_pubPat.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0090_lists.fram b/test/ok/ok0090_lists.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0091_namedParamMethod.fram b/test/ok/ok0091_namedParamMethod.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0092_multipleNamedMethodParams.fram b/test/ok/ok0092_multipleNamedMethodParams.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0093_specialBinops.fram b/test/ok/ok0093_specialBinops.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0094_unaryIf.fram b/test/ok/ok0094_unaryIf.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0095_wildcardTypeParam.fram b/test/ok/ok0095_wildcardTypeParam.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0096_fixTypeAnnot.fram b/test/ok/ok0096_fixTypeAnnot.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0097_recursion.fram b/test/ok/ok0097_recursion.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0098_mutualRecursion.fram b/test/ok/ok0098_mutualRecursion.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0099_nestedEffArrows.fram b/test/ok/ok0099_nestedEffArrows.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0100_polymorphicRecursion.fram b/test/ok/ok0100_polymorphicRecursion.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0101_implicitParamsRecord.fram b/test/ok/ok0101_implicitParamsRecord.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0102_simpleRecord.fram b/test/ok/ok0102_simpleRecord.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0103_genericRecords.fram b/test/ok/ok0103_genericRecords.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0104_chars.fram b/test/ok/ok0104_chars.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0105_recFunWithNamedParam.fram b/test/ok/ok0105_recFunWithNamedParam.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0106_recursiveMethod.fram b/test/ok/ok0106_recursiveMethod.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0107_polymorphicRecursion.fram b/test/ok/ok0107_polymorphicRecursion.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0108_modulePattern.fram b/test/ok/ok0108_modulePattern.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0109_fieldPattern.fram b/test/ok/ok0109_fieldPattern.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0110_publicModulePattern.fram b/test/ok/ok0110_publicModulePattern.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0111_optionalParams.fram b/test/ok/ok0111_optionalParams.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0112_pureRecord.fram b/test/ok/ok0112_pureRecord.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0113_pureMatchingNonrecUVar.fram b/test/ok/ok0113_pureMatchingNonrecUVar.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0114_pureTail.fram b/test/ok/ok0114_pureTail.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0115_purePatternMatching.fram b/test/ok/ok0115_purePatternMatching.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0116_pureRecordAccessor.fram b/test/ok/ok0116_pureRecordAccessor.fram old mode 100644 new mode 100755 diff --git a/test/ok/ok0117_comments.fram b/test/ok/ok0117_comments.fram old mode 100644 new mode 100755 diff --git a/test/stdlib/stdlib0000_Int64.fram b/test/stdlib/stdlib0000_Int64.fram old mode 100644 new mode 100755 diff --git a/test/stdlib/stdlib0001_Map.fram b/test/stdlib/stdlib0001_Map.fram deleted file mode 100644 index 01c19835..00000000 --- a/test/stdlib/stdlib0001_Map.fram +++ /dev/null @@ -1,81 +0,0 @@ -import Map -import open List -import open Prelude - -let lt (v1 : Int) (v2 : Int) = - if v1 < v2 then Less - else if v2 < v1 then Greater - else Equal - -let Map.Map {module IntMap} = Map.make lt - -let x = IntMap.empty - -(* insert check *) -let y = x.insert 1 1 -let z = x.insert 1 "a" - -(* isEmpty check *) -let _ = assert (y.isEmpty == False) "Failed isEmpty" -let _ = assert (z.isEmpty == False) "Failed isEmpty" -let _ = assert (y.remove 1 >. isEmpty) "Failed isEmpty" - -(* domain check *) -let z = y.insert 2 1 >. insert 3 2 >. insert 4 3 -let _ = assert (z.domain == [1,2,3,4] && z.toValueList == [1,1,2,3]) "Failed domain" - -(* toList check *) -let _ = assert ((z.toList.foldLeft - (fn acc (key,val) => val :: acc) []) == [1,1,2,3].rev) "Failed toList" - -(* foldl check *) -let _ = assert (z.foldl (fn key val acc => key :: acc) [] == [1,2,3,4].rev) - "Failed foldl" - -(* member check *) -let _ = assert (z.member 1) "Failed member" - -(* find check *) -let _ = assert (match z.find 1 with | None => False | _ => True end) "Failed find" - -(* operate change check *) -let _ = assert (snd (z.operate 1 (fn () => Some 2) (fn a => Some 0)) - >. toValueList == [0,1,2,3]) "Failed operate" - -(* operate add check *) -let _ = assert (snd (z.operate 0 (fn () => Some 2) (fn a => Some 0)) - >. toValueList == [2,1,1,2,3]) "Failed operate" - -(* map check *) -let _ = assert (z.mapVal (fn x => if x == x.shiftr 1 >. shiftl 1 then -x else x) - >. toValueList == [1,1,(0-2),3]) "Failed map" - -(* union check *) -let y = x.insert 1.neg 2 >. insert 2.neg 3 >. insert 0 1 >. insert 1 10 -let w = z.union y (fn key val1 val2 => val2) -let _ = assert (w.toValueList == [3,2,1,10,1,2,3]) "Failed union" - -(* partion check *) -let q = w.partion 0 -let _ = assert (fst (fst q) >. toValueList == [3,2]) "Failed partion" -let _ = assert (snd q >. toValueList == [10,1,2,3]) "Failed partion" - -(* partionLt check *) -let q = w.partionLt 0 -let _ = assert (fst q >. toValueList == [3,2,1]) "Failed partionLt" -let _ = assert (snd q >. toValueList == [10,1,2,3]) "Failed partionLt" - -(* partionGt check *) -let q = w.partionGt 0 -let _ = assert (fst q >. toValueList == [3,2]) "Failed partionGt" -let _ = assert (snd q >. toValueList == [1,10,1,2,3]) "Failed partionGt" - -(* range check *) -let q = w.range (Map.Exclusion 0) (Map.Exclusion 2) -let _ = assert (q.toValueList == [10]) "Failed range" -let q = w.range (Map.Inclusion 0) (Map.Inclusion 2) -let _ = assert (q.toValueList == [1,10,1]) "Failed range" -let _ = assert (w.range (Map.Inclusion 0) (Map.Exclusion 2) >. toValueList == [1,10]) - "Failed range" -let _ = assert (w.range (Map.Exclusion 0) (Map.Inclusion 2) >. toValueList == [10,1]) - "Failed range" diff --git a/test/stdlib/stdlib0001_Option.fram b/test/stdlib/stdlib0001_Option.fram old mode 100644 new mode 100755 diff --git a/test/stdlib/stdlib0002_Map.fram b/test/stdlib/stdlib0002_Map.fram new file mode 100755 index 00000000..34f5df2c --- /dev/null +++ b/test/stdlib/stdlib0002_Map.fram @@ -0,0 +1,88 @@ +import Map +import open List +import open Prelude + +let lt (v1 : Int) (v2 : Int) = + if v1 < v2 then Less + else if v2 < v1 then Greater + else Equal + +let Map.Map {module IntMap} = Map.make lt + +let x = IntMap.empty + +# insert check +let y = x.insert 1 1 +let z = x.insert 1 "a" + +# isEmpty check +let _ = assert {msg="Failed isEmpty"} (y.isEmpty == False) +let _ = assert {msg="Failed isEmpty"} (z.isEmpty == False) +let _ = assert {msg="Failed isEmpty"} (y.remove 1 >. isEmpty) + +# domain check +let z = y.insert 2 1 >. insert 3 2 >. insert 4 3 +let _ = assert {msg="Failed domain"} + (z.domain == [1,2,3,4] && z.toValueList == [1,1,2,3]) + +# toList check +let _ = assert {msg="Failed toList"} ((z.toList.foldLeft + (fn acc (key,val) => val :: acc) []) == [1,1,2,3].rev) + +# foldl check +let _ = assert {msg="Failed foldl"} + (z.foldl (fn key val acc => key :: acc) [] == [1,2,3,4].rev) + + +# member check +let _ = assert {msg="Failed member"} (z.member 1) + +# find check +let _ = assert {msg="Failed find"} + (match z.find 1 with | None => False | _ => True end) + +# operate change check +let _ = assert {msg="Failed operate"} + (snd (z.operate 1 (fn () => Some 2) (fn a => Some 0)) + >. toValueList == [0,1,2,3]) + +# operate add check +let _ = assert {msg="Failed operate"} + (snd (z.operate 0 (fn () => Some 2) (fn a => Some 0)) + >. toValueList == [2,1,1,2,3]) + +# map check +let _ = assert {msg="Failed map"} + (z.mapVal (fn x => if x == x.shiftr 1 >. shiftl 1 then -x else x) + >. toValueList == [1,1,(0-2),3]) + +# union check +let y = x.insert 1.neg 2 >. insert 2.neg 3 >. insert 0 1 >. insert 1 10 +let w = z.union y (fn key val1 val2 => val2) +let _ = assert {msg="Failed union"} (w.toValueList == [3,2,1,10,1,2,3]) + +# partion check +let q = w.partion 0 +let _ = assert {msg="Failed partion"} (fst (fst q) >. toValueList == [3,2]) +let _ = assert {msg="Failed partion"} (snd q >. toValueList == [10,1,2,3]) + +# partionLt check +let q = w.partionLt 0 +let _ = assert {msg="Failed partionLt"} (fst q >. toValueList == [3,2,1]) +let _ = assert {msg="Failed partionLt"} (snd q >. toValueList == [10,1,2,3]) + +# partionGt check +let q = w.partionGt 0 +let _ = assert {msg="Failed partionGt"} (fst q >. toValueList == [3,2]) +let _ = assert {msg="Failed partionGt"} (snd q >. toValueList == [1,10,1,2,3]) + +# range check +let q = w.range (Map.Exclusion 0) (Map.Exclusion 2) +let _ = assert {msg="Failed range"} (q.toValueList == [10]) +let q = w.range (Map.Inclusion 0) (Map.Inclusion 2) +let _ = assert {msg="Failed range"} (q.toValueList == [1,10,1]) +let _ = assert {msg="Failed range"} + (w.range (Map.Inclusion 0) (Map.Exclusion 2) >. toValueList == [1,10]) +let _ = assert {msg="Failed range"} + (w.range (Map.Exclusion 0) (Map.Inclusion 2) >. toValueList == [10,1]) + diff --git a/test/stdlib/stdlib0002_Set.fram b/test/stdlib/stdlib0002_Set.fram deleted file mode 100644 index 4b313b23..00000000 --- a/test/stdlib/stdlib0002_Set.fram +++ /dev/null @@ -1,72 +0,0 @@ -import Set -import open List -import open Prelude - -let lt (v1 : Int) (v2 : Int) = - if v1 < v2 then Less - else if v2 < v1 then Greater - else Equal - -let Set.Set {module IntSet} = Set.make lt - -(* empty check *) -let x = IntSet.empty -let _ = assert (x.isEmpty) "Failed empty" - -let x = x.insert 0 - -(* toList check *) -let _ = assert (x.toList == [0]) "Failed toList" - -(* insert check *) -let y = x.insert 1 -let _ = assert (y.toList == [0,1]) "Failed insert" -let _ = assert (y.insert 2 >. toList == [0,1,2]) "Failed insert" - -(* remove check *) -let y = y.insert 2 >. insert 3 -let _ = assert (y.remove 1 >. toList == [0,2,3]) "Failed remove" - -(* member check *) -let _ = assert (y.member 1) "Failed check" -let _ = assert (not (y.member 10)) "Failed check" - -(* foldl/r check *) -let _ = assert (y.foldl (fn x acc => x + acc) 0 == 6) "Failed foldl" -let _ = assert (y.foldr (fn x acc => x + acc) 0 == 6) "Failed foldr" - -(* union check *) -let x = x.insert 4 >. insert 5 >. insert 6 -let _ = assert (y.union x >. toList == [0,1,2,3,4,5,6]) "Failed union" - -(* intersection check *) -let _ = assert (x.intersection y >. toList == [0]) "Failed intersection" - -(* diffrence check *) -let _ = assert (y.difference x >. toList == [1,2,3]) "Failed difference" -let _ = assert (x.difference y >. toList == [4,5,6]) "Failed difference" - -(* eq check *) -let _ = assert (x.eq x) "Failed eq" -let _ = assert (not (x.eq y)) "Failed eq" - -(* subset check *) -let _ = assert (IntSet.empty.subset x) "Failed subset" -let _ = assert (IntSet.empty.insert 0 >. insert 1 >. subset y) "Failed subset" -let _ = assert (not (x.subset y)) "Failed subset" - -(* partionLt check *) -let _ = assert (fst (y.partionLt 2) >. toList == [0,1]) "Failed partionLt" -let _ = assert (snd (y.partionLt 2) >. toList == [2,3]) "Failed partionLt" - -(* range check *) -let _ = - assert (y.range (Set.Inclusion 1) (Set.Inclusion 2) >. toList == [1,2]) "Failed range" - -(* lowerBound check *) -let _ = - assert (match y.lowerBound with | Some x => x == 0 | _ => False end) "Failed lowerBound" - -(* upperBound check *) -let _ = assert (match y.upperBound with | Some x => x == 3 | _ => False end) - "Failed upperBound" diff --git a/test/stdlib/stdlib0003_Queue.fram b/test/stdlib/stdlib0003_Queue.fram deleted file mode 100644 index 159bfc34..00000000 --- a/test/stdlib/stdlib0003_Queue.fram +++ /dev/null @@ -1,22 +0,0 @@ -import Queue -import Prelude -import List - -let compare (x : Int) (y : Int) = x == y -let get_val x = -match x with -| Some x => x -| _ => -1 -end - -let x = Queue.emptyQueue -let x = x.push 1 -let _ = assert (x.isEmpty == False && compare (get_val x.head) 1) "Failed push" -let x = x.pop -let _ = assert x.isEmpty "Failed isEmpty" -let x = x >. push 1 >. push 2 >. push 3 -let _ = assert (x.isEmpty == False && compare (get_val x.head) 1 && - compare (get_val (x.pop >. head)) 2 && - compare (get_val (x.pop >. pop >. head)) 3) "Failed head and pop" -let x = Queue.fromList [1,2,3] -let _ = assert (x.toList == [1,2,3]) "Failed toList and fromList" \ No newline at end of file diff --git a/test/stdlib/stdlib0003_Set.fram b/test/stdlib/stdlib0003_Set.fram new file mode 100755 index 00000000..35ac391c --- /dev/null +++ b/test/stdlib/stdlib0003_Set.fram @@ -0,0 +1,76 @@ +import Set +import open List +import open Prelude + +let lt (v1 : Int) (v2 : Int) = + if v1 < v2 then Less + else if v2 < v1 then Greater + else Equal + +let Set.Set {module IntSet} = Set.make lt + +# empty check +let x = IntSet.empty +let _ = assert {msg="Failed empty"} (x.isEmpty) + +let x = x.insert 0 + +# toList check +let _ = assert {msg="Failed toList"} (x.toList == [0]) + +# insert check +let y = x.insert 1 +let _ = assert {msg="Failed insert"} (y.toList == [0,1]) +let _ = assert {msg="Failed insert"} (y.insert 2 >. toList == [0,1,2]) + +# remove check +let y = y.insert 2 >. insert 3 +let _ = assert {msg="Failed remove"} (y.remove 1 >. toList == [0,2,3]) + +# member check +let _ = assert {msg="Failed check"} (y.member 1) +let _ = assert {msg="Failed check"} (not (y.member 10)) + +# foldl/r check +let _ = assert {msg="Failed foldl"} (y.foldl (fn x acc => x + acc) 0 == 6) +let _ = assert {msg="Failed foldr"} (y.foldr (fn x acc => x + acc) 0 == 6) + +# union check +let x = x.insert 4 >. insert 5 >. insert 6 +let _ = assert {msg="Failed union"} (y.union x >. toList == [0,1,2,3,4,5,6]) + +# intersection check +let _ = assert {msg="Failed intersection"} (x.intersection y >. toList == [0]) + +# diffrence check +let _ = assert {msg="Failed difference"} (y.difference x >. toList == [1,2,3]) +let _ = assert {msg="Failed difference"} (x.difference y >. toList == [4,5,6]) + +# eq check +let _ = assert {msg="Failed eq"} (x.eq x) +let _ = assert {msg="Failed eq"} (not (x.eq y)) + +# subset check +let _ = assert {msg="Failed subset"} (IntSet.empty.subset x) +let _ = assert {msg="Failed subset"} + (IntSet.empty.insert 0 >. insert 1 >. subset y) +let _ = assert {msg="Failed subset"} (not (x.subset y)) + +# partionLt check +let _ = assert {msg="Failed partionLt"} + (fst (y.partionLt 2) >. toList == [0,1]) +let _ = assert {msg="Failed partionLt"} + (snd (y.partionLt 2) >. toList == [2,3]) + +# range check +let _ = assert {msg="Failed range"} + (y.range True 1 True 2 >. toList == [1,2]) + +# lowerBound check +let _ = assert {msg="Failed lowerBound"} + (match y.lowerBound with | Some x => x == 0 | _ => False end) + +# upperBound check +let _ = assert {msg="Failed upperBound"} + (match y.upperBound with | Some x => x == 3 | _ => False end) + diff --git a/test/stdlib/stdlib0004_Queue.fram b/test/stdlib/stdlib0004_Queue.fram new file mode 100755 index 00000000..fb0fd636 --- /dev/null +++ b/test/stdlib/stdlib0004_Queue.fram @@ -0,0 +1,24 @@ +import Queue +import Prelude +import List + +let compare (x : Int) (y : Int) = x == y +let get_val x = +match x with +| Some x => x +| _ => -1 +end + +let x = Queue.emptyQueue +let x = x.push 1 +let _ = assert {msg="Failed push"} + (x.isEmpty == False && compare (get_val x.head) 1) +let x = x.pop +let _ = assert {msg="Failed isEmpty"} x.isEmpty +let x = x >. push 1 >. push 2 >. push 3 +let _ = assert {msg="Failed head and pop"} + (x.isEmpty == False && compare (get_val x.head) 1 && + compare (get_val (x.pop >. head)) 2 && + compare (get_val (x.pop >. pop >. head)) 3) +let x = Queue.fromList [1,2,3] +let _ = assert {msg="Failed toList and fromList"} (x.toList == [1,2,3]) \ No newline at end of file diff --git a/test/test_suite b/test/test_suite old mode 100644 new mode 100755 From 2904ee7e2de31dd7424c29de2b6815fd22cde10f Mon Sep 17 00:00:00 2001 From: Jakub Chomiczewski Date: Thu, 20 Feb 2025 15:57:06 +0100 Subject: [PATCH 20/27] Adding comments --- lib/Map.fram | 136 ++++++++++++++++++++++++++++++-- lib/Set.fram | 31 +++++++- test/stdlib/stdlib0002_Map.fram | 8 +- 3 files changed, 162 insertions(+), 13 deletions(-) diff --git a/lib/Map.fram b/lib/Map.fram index d5eab927..17eeb438 100755 --- a/lib/Map.fram +++ b/lib/Map.fram @@ -8,22 +8,50 @@ import open RedBlackTree # Signature #} -pub data Interval Value = Inclusion of Value | Exclusion of Value +data Interval Value = Inclusion of Value | Exclusion of Value implicit ~onError pub data Map Key = Map of { T + {# @brief Creates empty map + #} , empty : {type Val} -> T Val + {# @brief Method to testing whether given map is empty or not + # @return True if it's empty false otherwise + #} , method isEmpty : {type Val} -> T Val -> [] Bool + {# @brief Method for inserting element to the map + # @param Key which will be inserted to the map + # @param Value which will be inserted to the map + # @return Map with inserted value + #} , method insert : {type Val} -> T Val -> Key -> Val -> [] T Val + {# @brief Method for inserting element to the map + # @param Key which will be inserted to the map + # @param Value which will be inserted to the map + # @return Map with inserted value + and boolean value if the value was changed + if the key already existed in map + #} , method insertChange : {type Val} -> T Val -> Key -> Val -> [] (Pair (T Val) Bool) + {# @brief Method for removing key from the map + # @param Key which will be removed to the map + # @return Map with removed key + #} , method remove : {type Val} -> T Val -> Key -> [] T Val + {# @brief Method for removing key from the map + # @param Key which will be removed to the map + # @return Map with removed key + and boolean value if the map was changed + #} , method removeChange : {type Val} -> T Val -> Key -> [] (Pair (T Val) Bool) + {# @brief Method for checking if a given key is present in a map + #} , method member : {type Val} -> T Val -> Key -> [] Bool , method find : {type Val} -> T Val -> Key -> [] Option Val {# @brief method that searches for an item and returns value @@ -37,54 +65,142 @@ pub data Map Key = Map of { , method operate : {type Val,E} -> T Val -> Key -> (Unit -> [|E] Option Val) -> (Val -> [|E] Option Val) -> [|E] (Pair (Pair (Option Val) (Option Val)) (T Val)) + {# @brief Method to fold left through structure of map + # @param Function that receives key, value and accumulator + # @param Accumulator + # @return Result of applying function on keys + and values of map and accumulator + #} , method foldl : {type Val, type A,E} -> T Val -> (Key -> Val -> A -> [|E] A) -> A -> [|E] A + {# @brief Method to fold right through structure of map + # @param Function that receives key, value and accumulator + # @param Accumulator + # @return Result of applying function on keys + and values of map and accumulator + #} , method foldr : {type Val, type A,E} -> T Val -> (Key -> Val -> A -> [|E] A) -> A -> [|E] A + {# @brief Method that returns list of pairs (key,value) + #} , method toList : {type Val} -> T Val -> [] List (Pair Key Val) + {# @brief Method that returns list of values + #} , method toValueList : {type Val} -> T Val -> [] List Val + {# @brief Method that returns list of keys + #} , method domain : {type Val} -> T Val -> [] List Key + {# @brief Method that maps all values in a map to diffrent value + #} , method mapVal : {type Val, type A,E} -> T Val -> (Val -> [|E] A) -> [|E] T A + {# @brief Method that maps all (key,value) in a map to (key, func key) + #} , method mapKey : {type Val, type A,E} -> T Val -> (Key -> [|E] A) -> [|E] T A + {# @brief Method that applies function to every key and value + #} , method app : {type Val,E} -> T Val -> (Key -> Val -> [|E] Unit) -> [|E] Unit + {# @brief Method that joins two maps + # @param Function that resolves conflicts + # if maps have the same key + #} , method union : {type Val,E} -> T Val -> T Val -> (Key -> Val -> Val -> [|E] Val) -> [|E] T Val + {# @brief Method that splits map into two maps one with + # the keys lower then given key, the other with greater. + # @return map with lower keys, Some value if key was present, + # map with greater keys + #} , method partion : {type Val} -> T Val -> Key -> [] (Pair (Pair (T Val) (Option Val)) (T Val)) + {# @brief Method that splits map into two maps one with + # the keys lower then given key, the other with greater or equal. + #} , method partionLt : {type Val} -> T Val -> Key -> [] Pair (T Val) (T Val) + {# @brief Method that splits map into two maps one with + # the keys lower or equal then given key, the other with greater. + #} , method partionGt : {type Val} -> T Val -> Key -> [] Pair (T Val) (T Val) - , method range : {type Val} -> T Val -> Interval Key -> - Interval Key -> [] T Val + {# @brief Method that gives a submap in a given range + # @param First Bool - if the submap should include lower key or not + # @param First Elem - lower key which all elements + # in returned map will be greater (or equal) + # @param Second Bool - if the submap should include upper key or not + # @param Second Elem - upper key which all elements + # in returned map will be lower (or equal) + # @return Submap in a given range + #} + , method range : {type Val} -> T Val -> Bool -> Key -> + Bool -> Key -> [] T Val + {# @brief Method that returns lowest pair (key,value) in a map + # @return Some (key,value) if the smallest key exist or otherwise None + #} , method lowerBound : {type Val} -> T Val -> [] Option (Pair Key Val) + {# @brief Method that returns lowest pair (key,value) in a map + # @return (key,value) or error + #} , method lowerBoundErr : {type Val, Err, ~onError : Unit -> [Err] (Pair Key Val)} -> T Val -> [Err] (Pair Key Val) + {# @brief Method that returns greatest pair (key,value) in a map + # @return Some (key,value) if the greatest key exist or otherwise None + #} , method upperBound : {type Val} -> T Val -> [] Option (Pair Key Val) + {# @brief Method that returns greatest pair (key,value) in a map + # @return (key,value) or error + #} , method upperBoundErr : {type Val, Err, ~onError : Unit -> [Err] (Pair Key Val)} -> T Val -> [Err] (Pair Key Val) + {# @brief Method that returns the lowest (key,value) greater than given key + # @return Some (key,value) or None + #} , method lowerBoundGt : {type Val} -> T Val -> Key -> [] Option (Pair Key Val) + {# @brief Method that returns the lowest (key,value) greater than given key + # @return (key,value) or error + #} , method lowerBoundGtErr : {type Val, Err, ~onError : Unit -> [Err] (Pair Key Val)} -> T Val -> Key -> [Err] (Pair Key Val) + {# @brief Method that returns the lowest (key,value) greater + # or equal than given key + # @return Some (key,value) or None + #} , method lowerBoundGeq : {type Val} -> T Val -> Key -> [] Option (Pair Key Val) + {# @brief Method that returns the lowest (key,value) greater + # or equal than given key + # @return (key,value) or error + #} , method lowerBoundGeqErr : {type Val, Err, ~onError : Unit -> [Err] (Pair Key Val)} -> T Val -> Key -> [Err] (Pair Key Val) + {# @brief Method that returns the greatest (key,value) lower than given key + # @return Some (key,value) or None + #} , method upperBoundLt : {type Val} -> T Val -> Key -> [] Option (Pair Key Val) + {# @brief Method that returns the greatest (key,value) lower than given key + # @return (key,value) or error + #} , method upperBoundLtErr : {type Val, Err, ~onError : Unit -> [Err] (Pair Key Val)} -> T Val -> Key -> [Err] (Pair Key Val) + {# @brief Method that returns the greatest (key,value) lower + # or equal than given key + # @return Some (key,value) or None + #} , method upperBoundLeq : {type Val,E} -> T Val -> Key -> [] Option (Pair Key Val) + {# @brief Method that returns the greatest (key,value) lower + # or equal than given key + # @return (key,value) or error + #} , method upperBoundLeqErr : {type Val, Err, ~onError : Unit -> [Err] (Pair Key Val)} -> T Val -> Key -> [Err] (Pair Key Val) @@ -364,7 +480,7 @@ let partion compare tree key = | Some (_,x) => (left,Some x, right) end -let range compare tree left right = +let _range compare tree left right = match (left,right) with | (Inclusion left, Inclusion right) => let (_,middle) = partionGt compare tree left in @@ -380,6 +496,14 @@ let range compare tree left right = let (result,_) = partionGt compare middle right in result end +let range compare tree incl left incr right = + match (incl,incr) with + | (False,False) => _range compare tree (Exclusion left) (Exclusion right) + | (False,True) => _range compare tree (Exclusion left) (Inclusion right) + | (True,False) => _range compare tree (Inclusion left) (Exclusion right) + | (True,True) => _range compare tree (Inclusion left) (Inclusion right) + end + data MapT Key Val = MapT of Tree (Pair Key Val) # Wrappers @@ -434,8 +558,8 @@ let partionGtT compare (MapT tree) key = let (t1,t2) = partionGt compare tree key in (MapT t1, MapT t2) -let rangeT compare (MapT tree) left right = - MapT (range compare tree left right) +let rangeT compare (MapT tree) incl left incr right = + MapT (range compare tree incl left incr right) let lowerBoundT (MapT tree) = lowerBound tree diff --git a/lib/Set.fram b/lib/Set.fram index f4ef8481..0e1af613 100755 --- a/lib/Set.fram +++ b/lib/Set.fram @@ -111,24 +111,49 @@ pub data Set Elem = Set of { # @return Some value if the greatest element exist or otherwise None #} , method upperBound : T -> [] Option Elem - {# @brief Method that returns the greates stored value in a set + {# @brief Method that returns the greatest stored value in a set # @return greatest element or error #} , method upperBoundErr : {Err, ~onError : Unit -> [Err] Elem} -> T -> [Err] Elem - {# - + {# @brief Method that returns the lowest element greater than given element + # @return Some value or None #} , method lowerBoundGt : T -> Elem -> [] Option Elem + {# @brief Method that returns the lowest element greater than given element + # @return value or error + #} , method lowerBoundGtErr : {Err, ~onError : Unit -> [Err] Elem} -> T -> Elem -> [Err] Elem + {# @brief Method that returns the lowest element greater + # or equal than given element + # @return Some value or None + #} , method lowerBoundGeq : T -> Elem -> [] Option Elem + {# @brief Method that returns the lowest element greater + # or equal than given element + # @return value or error + #} , method lowerBoundGeqErr : {Err, ~onError : Unit -> [Err] Elem} -> T -> Elem -> [Err] Elem + {# @brief Method that returns the greatest element lower than given element + # @return Some value or None + #} , method upperBoundLt : T -> Elem -> [] Option Elem + {# @brief Method that returns the greatest element lower than given element + # @return value or error + #} , method upperBoundLtErr : {Err, ~onError : Unit -> [Err] Elem} -> T -> Elem -> [Err] Elem + {# @brief Method that returns the greatest element lower + # or equal than given element + # @return Some value or None + #} , method upperBoundLeq : T -> Elem -> [] Option Elem + {# @brief Method that returns the greatest element lower + # or equal than given element + # @return value or error + #} , method upperBoundLeqErr : {Err, ~onError : Unit -> [Err] Elem} -> T -> Elem -> [Err] Elem } diff --git a/test/stdlib/stdlib0002_Map.fram b/test/stdlib/stdlib0002_Map.fram index 34f5df2c..0b798a4c 100755 --- a/test/stdlib/stdlib0002_Map.fram +++ b/test/stdlib/stdlib0002_Map.fram @@ -77,12 +77,12 @@ let _ = assert {msg="Failed partionGt"} (fst q >. toValueList == [3,2]) let _ = assert {msg="Failed partionGt"} (snd q >. toValueList == [1,10,1,2,3]) # range check -let q = w.range (Map.Exclusion 0) (Map.Exclusion 2) +let q = w.range False 0 False 2 let _ = assert {msg="Failed range"} (q.toValueList == [10]) -let q = w.range (Map.Inclusion 0) (Map.Inclusion 2) +let q = w.range True 0 True 2 let _ = assert {msg="Failed range"} (q.toValueList == [1,10,1]) let _ = assert {msg="Failed range"} - (w.range (Map.Inclusion 0) (Map.Exclusion 2) >. toValueList == [1,10]) + (w.range True 0 False 2 >. toValueList == [1,10]) let _ = assert {msg="Failed range"} - (w.range (Map.Exclusion 0) (Map.Inclusion 2) >. toValueList == [10,1]) + (w.range False 0 True 2 >. toValueList == [10,1]) From 74690614aad7dd9b6a52a8473a2f09cf5b268fd5 Mon Sep 17 00:00:00 2001 From: Szymon Jedras Date: Thu, 13 Mar 2025 00:00:31 +0100 Subject: [PATCH 21/27] Some (hopefully) final changes --- lib/Base/Types.fram | 3 + lib/Map.fram | 829 ++++++++++++++++---------------- lib/Prelude.fram | 4 - lib/Queue.fram | 82 ++-- lib/RedBlackTree.fram | 351 +++++++------- lib/Set.fram | 677 +++++++++++++------------- test/stdlib/stdlib0002_Map.fram | 109 +++-- test/stdlib/stdlib0003_Set.fram | 95 ++-- 8 files changed, 1066 insertions(+), 1084 deletions(-) diff --git a/lib/Base/Types.fram b/lib/Base/Types.fram index 454805d7..6f696399 100755 --- a/lib/Base/Types.fram +++ b/lib/Base/Types.fram @@ -11,3 +11,6 @@ pub data rec List A = [] | (::) of A, List A pub data Pair X Y = (,) of X, Y pub data Either X Y = Left of X | Right of Y + +pub data Ordered = Lt | Eq | Gt + diff --git a/lib/Map.fram b/lib/Map.fram index 17eeb438..5c08e383 100755 --- a/lib/Map.fram +++ b/lib/Map.fram @@ -8,359 +8,399 @@ import open RedBlackTree # Signature #} -data Interval Value = Inclusion of Value | Exclusion of Value - implicit ~onError pub data Map Key = Map of { - T - {# @brief Creates empty map - #} - , empty : {type Val} -> T Val - {# @brief Method to testing whether given map is empty or not - # @return True if it's empty false otherwise - #} - , method isEmpty : {type Val} -> T Val -> [] Bool - {# @brief Method for inserting element to the map - # @param Key which will be inserted to the map - # @param Value which will be inserted to the map - # @return Map with inserted value - #} - , method insert : {type Val} -> T Val -> - Key -> Val -> [] T Val - {# @brief Method for inserting element to the map - # @param Key which will be inserted to the map - # @param Value which will be inserted to the map - # @return Map with inserted value - and boolean value if the value was changed - if the key already existed in map - #} - , method insertChange : {type Val} -> T Val -> - Key -> Val -> [] (Pair (T Val) Bool) - {# @brief Method for removing key from the map - # @param Key which will be removed to the map - # @return Map with removed key - #} - , method remove : {type Val} -> T Val -> - Key -> [] T Val - {# @brief Method for removing key from the map - # @param Key which will be removed to the map - # @return Map with removed key - and boolean value if the map was changed - #} - , method removeChange : {type Val} -> T Val -> - Key -> [] (Pair (T Val) Bool) - {# @brief Method for checking if a given key is present in a map - #} - , method member : {type Val} -> T Val -> Key -> [] Bool - , method find : {type Val} -> T Val -> Key -> [] Option Val - {# @brief method that searches for an item and returns value - # based on the search - # @param key - # @param absentf what value return if the element doesn't exist - # @param presentf what value return if the element exist - # @return tuple of found an item and it's value, - # result of a given function absentf or presentf and orginal tree - #} - , method operate : {type Val,E} -> T Val -> Key -> - (Unit -> [|E] Option Val) -> (Val -> [|E] Option Val) -> - [|E] (Pair (Pair (Option Val) (Option Val)) (T Val)) - {# @brief Method to fold left through structure of map - # @param Function that receives key, value and accumulator - # @param Accumulator - # @return Result of applying function on keys - and values of map and accumulator - #} - , method foldl : {type Val, type A,E} -> T Val -> - (Key -> Val -> A -> [|E] A) -> A -> [|E] A - {# @brief Method to fold right through structure of map - # @param Function that receives key, value and accumulator - # @param Accumulator - # @return Result of applying function on keys - and values of map and accumulator - #} - , method foldr : {type Val, type A,E} -> T Val -> - (Key -> Val -> A -> [|E] A) -> A -> [|E] A - {# @brief Method that returns list of pairs (key,value) - #} - , method toList : {type Val} -> T Val -> [] List (Pair Key Val) - {# @brief Method that returns list of values - #} - , method toValueList : {type Val} -> T Val -> [] List Val - {# @brief Method that returns list of keys - #} - , method domain : {type Val} -> T Val -> [] List Key - {# @brief Method that maps all values in a map to diffrent value - #} - , method mapVal : {type Val, type A,E} -> T Val -> - (Val -> [|E] A) -> [|E] T A - {# @brief Method that maps all (key,value) in a map to (key, func key) - #} - , method mapKey : {type Val, type A,E} -> T Val -> - (Key -> [|E] A) -> [|E] T A - {# @brief Method that applies function to every key and value - #} - , method app : {type Val,E} -> T Val -> - (Key -> Val -> [|E] Unit) -> [|E] Unit - {# @brief Method that joins two maps - # @param Function that resolves conflicts - # if maps have the same key - #} - , method union : {type Val,E} -> T Val -> T Val -> - (Key -> Val -> Val -> [|E] Val) -> [|E] T Val - {# @brief Method that splits map into two maps one with - # the keys lower then given key, the other with greater. - # @return map with lower keys, Some value if key was present, - # map with greater keys - #} - , method partion : {type Val} -> T Val -> Key -> - [] (Pair (Pair (T Val) (Option Val)) (T Val)) - {# @brief Method that splits map into two maps one with - # the keys lower then given key, the other with greater or equal. - #} - , method partionLt : {type Val} -> T Val -> Key -> - [] Pair (T Val) (T Val) - {# @brief Method that splits map into two maps one with - # the keys lower or equal then given key, the other with greater. - #} - , method partionGt : {type Val} -> T Val -> Key -> - [] Pair (T Val) (T Val) - {# @brief Method that gives a submap in a given range - # @param First Bool - if the submap should include lower key or not - # @param First Elem - lower key which all elements - # in returned map will be greater (or equal) - # @param Second Bool - if the submap should include upper key or not - # @param Second Elem - upper key which all elements - # in returned map will be lower (or equal) - # @return Submap in a given range - #} - , method range : {type Val} -> T Val -> Bool -> Key -> - Bool -> Key -> [] T Val - {# @brief Method that returns lowest pair (key,value) in a map - # @return Some (key,value) if the smallest key exist or otherwise None - #} - , method lowerBound : {type Val} -> T Val -> [] Option (Pair Key Val) - {# @brief Method that returns lowest pair (key,value) in a map - # @return (key,value) or error - #} - , method lowerBoundErr : - {type Val, Err, ~onError : Unit -> [Err] (Pair Key Val)} -> - T Val -> [Err] (Pair Key Val) - {# @brief Method that returns greatest pair (key,value) in a map - # @return Some (key,value) if the greatest key exist or otherwise None - #} - , method upperBound : {type Val} -> T Val -> [] Option (Pair Key Val) - {# @brief Method that returns greatest pair (key,value) in a map - # @return (key,value) or error - #} - , method upperBoundErr : - {type Val, Err, ~onError : Unit -> [Err] (Pair Key Val)} -> - T Val -> [Err] (Pair Key Val) - {# @brief Method that returns the lowest (key,value) greater than given key - # @return Some (key,value) or None - #} - , method lowerBoundGt : {type Val} -> T Val -> Key -> - [] Option (Pair Key Val) - {# @brief Method that returns the lowest (key,value) greater than given key - # @return (key,value) or error - #} - , method lowerBoundGtErr : - {type Val, Err, ~onError : Unit -> [Err] (Pair Key Val)} -> - T Val -> Key -> [Err] (Pair Key Val) - {# @brief Method that returns the lowest (key,value) greater - # or equal than given key - # @return Some (key,value) or None - #} - , method lowerBoundGeq : {type Val} -> T Val -> Key -> - [] Option (Pair Key Val) - {# @brief Method that returns the lowest (key,value) greater - # or equal than given key - # @return (key,value) or error - #} - , method lowerBoundGeqErr : - {type Val, Err, ~onError : Unit -> [Err] (Pair Key Val)} -> - T Val -> Key -> [Err] (Pair Key Val) - {# @brief Method that returns the greatest (key,value) lower than given key - # @return Some (key,value) or None - #} - , method upperBoundLt : {type Val} -> T Val -> - Key -> [] Option (Pair Key Val) - {# @brief Method that returns the greatest (key,value) lower than given key - # @return (key,value) or error - #} - , method upperBoundLtErr : - {type Val, Err, ~onError : Unit -> [Err] (Pair Key Val)} -> - T Val -> Key -> [Err] (Pair Key Val) - {# @brief Method that returns the greatest (key,value) lower - # or equal than given key - # @return Some (key,value) or None - #} - , method upperBoundLeq : {type Val,E} -> T Val -> - Key -> [] Option (Pair Key Val) - {# @brief Method that returns the greatest (key,value) lower - # or equal than given key - # @return (key,value) or error - #} - , method upperBoundLeqErr : - {type Val, Err, ~onError : Unit -> [Err] (Pair Key Val)} -> - T Val -> Key -> [Err] (Pair Key Val) + T + + {## @brief Creates empty map + ##} + , empty : {type Val} -> T Val + + {## @brief Method to testing whether given map is empty or not + # @return True if it's empty false otherwise + ##} + , method isEmpty : {type Val} -> T Val ->[] Bool + + {## @brief Method for inserting element to the map + # @param Key which will be inserted to the map + # @param Value which will be inserted to the map + # @return Map with inserted value + ##} + , method insert : {type Val} -> T Val -> + Key -> Val ->[] T Val + + {## @brief Method for inserting element to the map + # @param Key which will be inserted to the map + # @param Value which will be inserted to the map + # @return Map with inserted value + # and boolean value if the value was changed + # if the key already existed in map + ##} + , method insertChange : {type Val} -> T Val -> + Key -> Val ->[] (Pair (T Val) Bool) + + {## @brief Method for removing key from the map + # @param Key which will be removed to the map + # @return Map with removed key + ##} + , method remove : {type Val} -> T Val -> Key ->[] T Val + + {## @brief Method for removing key from the map + # @param Key which will be removed to the map + # @return Map with removed key + # and boolean value if the map was changed + ##} + , method removeChange : {type Val} -> T Val -> + Key ->[] (Pair (T Val) Bool) + + {## @brief Method for checking if a given key is present in a map + ##} + , method member : {type Val} -> T Val -> Key ->[] Bool + + {## @brief Method for getting value mapping from a key + # returns None if key is not found + ##} + , method find : {type Val} -> T Val -> Key ->[] Option Val + + {## @brief Method for getting value mapping from a key, + # calls `~onError` if key is not found + ##} + , method findErr : + {type Val, Err, ~onError : Unit ->[Err] Val} -> T Val -> Key ->[Err] Val + + {## @brief Method to update mapping on a key using a function + # @param key + # @param f is called with Option Val based on if the key has mapping + # in the input tree and should return Option Val to update the tree + # @return updated tree + ##} + , method update : {type Val,E} -> T Val -> Key -> + (Option Val ->[|E] Option Val) ->[|E] T Val + + {## @brief Method to fold left through structure of map + # @param Function that receives key, value and accumulator + # @param Accumulator + # @return Result of applying function on keys + # and values of map and accumulator + ##} + , method foldl : {type Val, type A,E} -> T Val -> + (Key -> Val -> A ->[|E] A) -> A ->[|E] A + + {## @brief Method to fold right through structure of map + # @param Function that receives key, value and accumulator + # @param Accumulator + # @return Result of applying function on keys + # and values of map and accumulator + ##} + , method foldr : {type Val, type A,E} -> T Val -> + (Key -> Val -> A ->[|E] A) -> A ->[|E] A + + {## @brief Method that returns list of pairs (key,value) + ##} + , method toList : {type Val} -> T Val ->[] List (Pair Key Val) + + {## @brief Method that returns list of values + ##} + , method toValueList : {type Val} -> T Val ->[] List Val + + {## @brief Method that returns list of keys + ##} + , method domain : {type Val} -> T Val ->[] List Key + + {## @brief Method that maps all values using given function + ##} + , method mapVal : {type Val, type A, E} -> T Val -> + (Val ->[|E] A) ->[|E] T A + + {## @brief Method that maps all (key,value) in a map to (key, func key) + ##} + , method mapKey : {type Val, type A,E} -> T Val -> + (Key ->[|E] A) ->[|E] T A + + {## @brief Method that applies function to every key and value + ##} + , method iter : {type Val,E} -> T Val -> + (Key -> Val ->[|E] Unit) ->[|E] Unit + + {## @brief Method that joins two maps + # @param Function that resolves conflicts + # if maps have the same key + ##} + , method union : {type Val,E} -> T Val -> T Val -> + (Key -> Val -> Val ->[|E] Val) ->[|E] T Val + + {## @brief Method that splits map into two maps one with + # the keys lower then given key, the other with greater. + # @return map with lower keys, Some value if key was present, + # map with greater keys + ##} + , method partion : {type Val} -> T Val -> Key ->[] + (Pair (Pair (T Val) (Option Val)) (T Val)) + + {## @brief Method that splits map into two maps one with + # the keys lower then given key, the other with greater or equal. + ##} + , method partionLt : {type Val} -> T Val -> Key ->[] Pair (T Val) (T Val) + + {## @brief Method that splits map into two maps one with + # the keys lower or equal then given key, the other with greater. + ##} + , method partionGt : {type Val} -> T Val -> Key ->[] Pair (T Val) (T Val) + + {## @brief Method that returns lowest pair (key,value) in a map + # @return Some (key,value) if the smallest key exist or otherwise None + ##} + , method lowerBound : {type Val} -> T Val ->[] Option (Pair Key Val) + + {## @brief Method that returns lowest pair (key,value) in a map + # @return (key,value) or error + ##} + , method lowerBoundErr : + {type Val, Err, ~onError : Unit ->[Err] (Pair Key Val)} -> + T Val ->[Err] (Pair Key Val) + + {## @brief Method that returns greatest pair (key,value) in a map + # @return Some (key,value) if the greatest key exist or otherwise None + ##} + , method upperBound : {type Val} -> T Val ->[] Option (Pair Key Val) + + {## @brief Method that returns greatest pair (key,value) in a map + # @return (key,value) or error + ##} + , method upperBoundErr : + {type Val, Err, ~onError : Unit ->[Err] (Pair Key Val)} -> + T Val ->[Err] (Pair Key Val) + + {## @brief Method that returns the lowest (key,value) greater than given key + # @return Some (key,value) or None + ##} + , method lowerBoundGt : {type Val} -> T Val -> Key ->[] + Option (Pair Key Val) + + {## @brief Method that returns the lowest (key,value) greater than given key + # @return (key,value) or error + ##} + , method lowerBoundGtErr : + {type Val, Err, ~onError : Unit ->[Err] (Pair Key Val)} -> + T Val -> Key ->[Err] (Pair Key Val) + + {## @brief Method that returns the lowest (key,value) greater + # or equal than given key + # @return Some (key,value) or None + ##} + , method lowerBoundGeq : {type Val} -> T Val -> Key ->[] + Option (Pair Key Val) + + {## @brief Method that returns the lowest (key,value) greater + # or equal than given key + # @return (key,value) or error + ##} + , method lowerBoundGeqErr : + {type Val, Err, ~onError : Unit ->[Err] (Pair Key Val)} -> + T Val -> Key ->[Err] (Pair Key Val) + + {## @brief Method that returns the greatest (key,value) lower than given key + # @return Some (key,value) or None + ##} + , method upperBoundLt : {type Val} -> T Val -> + Key ->[] Option (Pair Key Val) + + {## @brief Method that returns the greatest (key,value) lower than given key + # @return (key,value) or error + ##} + , method upperBoundLtErr : + {type Val, Err, ~onError : Unit ->[Err] (Pair Key Val)} -> + T Val -> Key ->[Err] (Pair Key Val) + + {## @brief Method that returns the greatest (key,value) lower + # or equal than given key + # @return Some (key,value) or None + ##} + , method upperBoundLeq : {type Val,E} -> T Val -> + Key ->[] Option (Pair Key Val) + + {## @brief Method that returns the greatest (key,value) lower + # or equal than given key + # @return (key,value) or error + ##} + , method upperBoundLeqErr : + {type Val, Err, ~onError : Unit ->[Err] (Pair Key Val)} -> + T Val -> Key ->[Err] (Pair Key Val) } -# implementation +# implementation + +let keyComp compare key (key', _) = compare key key' let isEmpty tree = - match tree with - | Leaf => True - | _ => False + match tree with + | Leaf => True + | _ => False end -let insert compare tree key val = - match search (fn (key', _ ) => compare key key') tree [] with - | (Leaf, zipper) => zipRed (key,val) Leaf Leaf zipper - | ((Node {color, size = bulk, left, right}), zipper) => - zip (construct color bulk left (key,val) right) zipper +let insert compare tree key val = + match search (keyComp compare key) tree [] with + | (Leaf, zipper) => zipRed (key,val) Leaf Leaf zipper + | ((Node {color, size, left, right}), zipper) => + zip (construct color size left (key,val) right) zipper end let insert' compare tree key val = - match search (fn (key', _ ) => compare key key') tree [] with - | (Leaf, zipper) => (zipRed (key,val) Leaf Leaf zipper, False) - | ((Node {color, size = bulk, left, right}), zipper) => - (zip (construct color bulk left (key,val) right) zipper, True) + match search (keyComp compare key) tree [] with + | (Leaf, zipper) => (zipRed (key,val) Leaf Leaf zipper, False) + | (Node {color, size, left, right}, zipper) => + (zip (construct color size left (key,val) right) zipper, True) end let remove compare tree key = - match search (fn (key', _ ) => compare key key') tree [] with - | (Leaf,_) => tree - | (Node {color, left, right}, zipper) => - delete color left right zipper + match search (keyComp compare key) tree [] with + | (Leaf,_) => tree + | (Node {color, left, right}, zipper) => + delete color left right zipper end let remove' compare tree key = - match search (fn (key', _ ) => compare key key') tree [] with - | (Leaf,_) => (tree,False) - | (Node {color, left, right}, zipper) => - (delete color left right zipper, True) + match search (keyComp compare key) tree [] with + | (Leaf,_) => (tree,False) + | (Node {color, left, right}, zipper) => + (delete color left right zipper, True) end let rec member compare tree key = match tree with - | Leaf => False - | Node {left, value = (key',_), right} => - match compare key key' with - | Less => member compare left key - | Equal => True - | Greater => member compare right key - end + | Leaf => False + | Node {left, value = (key',_), right} => + match compare key key' with + | Lt => member compare left key + | Eq => True + | Gt => member compare right key + end end let rec find compare tree key = - match tree with - | Leaf => None - | Node {left, value = (key', val), right} => - match compare key key' with - | Less => find compare left key - | Equal => Some val - | Greater => find compare right key - end - end + match tree with + | Leaf => None + | Node {left, value = (key', val), right} => + match compare key key' with + | Lt => find compare left key + | Eq => Some val + | Gt => find compare right key + end + end -let rec operate compare tree key absentf presentf = - match search (fn (key', _ ) => compare key key') tree [] with - | (Leaf, zipper) => match absentf () with - | None => (None,None, tree) - | Some x => (None,Some x, zipRed (key,x) Leaf Leaf zipper) +let rec findErr compare tree key = + match tree with + | Leaf => ~onError () + | Node {left, value = (key', val), right} => + match compare key key' with + | Lt => findErr compare left key + | Eq => val + | Gt => findErr compare right key end - | (Node {color, size = bulk, left, value = (_, val), right}, zipper) => - match presentf val with - | None => (Some val, None, delete color left right zipper) - | Some x => (Some val, Some x, zip - (construct color bulk left (key,x) right) zipper) + end + +let update compare tree key f = + match search (keyComp compare key) tree [] with + | (Leaf, zipper) => + match f None with + | None => tree + | Some x => zipRed (key,x) Leaf Leaf zipper end - end + | (Node {color, size, left, value = (_, val), right}, zipper) => + match f (Some val) with + | None => delete color left right zipper + | Some x => zip (construct color size left (key,x) right) zipper + end + end -let rec foldr func tree acc = +let rec foldr func tree acc = match tree with - | Leaf => acc - | Node {left, value = (key, val), right} => - let val_right = (foldr func right acc) in - let val_middle = (func key val val_right) in - foldr func left val_middle + | Leaf => acc + | Node {left, value = (key, val), right} => + let val_right = foldr func right acc + let val_middle = func key val val_right in + foldr func left val_middle end let rec foldl func tree acc = match tree with - | Leaf => acc - | Node {left, value = (key, val), right} => - let val_left = (foldl func left acc) in - let val_middle = (func key val val_left) - in foldl func right val_middle - end - -let rec map tree func = + | Leaf => acc + | Node {left, value = (key, val), right} => + let val_left = foldl func left acc + let val_middle = func key val val_left in + foldl func right val_middle + end + +let rec map tree func = match tree with - | Leaf => Leaf - | Node {color, size, left, value = (key,value), right} => - construct color size (map left func) (key,func value) (map right func) + | Leaf => Leaf + | Node {color, size, left, value = (key,value), right} => + let left' = map left func + let right' = map right func in + construct color size left' (key,func value) right' end -let rec map2 tree func = +let rec map2 tree func = match tree with - | Leaf => Leaf - | Node {color, size = bulk, left, value = (key, _), right} => - construct color bulk (map2 left func) (key, func key) (map2 right func) + | Leaf => Leaf + | Node {color, size, left, value = (key, _), right} => + let left' = map2 left func + let right' = map2 right func in + construct color size left' (key, func key) right' end -let rec app tree func = - match tree with - | Leaf => () - | Node {left, value = (key,value), right} => - app left func; func key value; app right func +let rec iter tree func = + match tree with + | Leaf => () + | Node {left, value = (key,value), right} => + iter left func; + func key value; + iter right func end -let rec union compare tree1 tree2 merge = +let rec union compare tree1 tree2 merge = match tree1 with | Leaf => tree2 | Node {left = left1, value = (key1,value1), right = right1} => - match tree2 with + match tree2 with | Leaf => tree1 - | _ => - let (output,left2,right2) = - split (fn (key2,_) => compare key1 key2) tree2 - in - let new_pair = - match output with - | None => (key1,value1) - | Some (_,value2) => (key1, merge key1 value1 value2) - end - in - joinVal (union compare left1 left2 merge) new_pair - (union compare right1 right2 merge) + | _ => + let (output,left2,right2) = split (keyComp compare key1) tree2 + let new_pair = + match output with + | None => (key1,value1) + | Some (_,value2) => (key1, merge key1 value1 value2) + end + let left' = union compare left1 left2 merge + let right' = union compare right1 right2 merge in + joinVal left' new_pair right' end end -let partionLt compare tree key = - let (_,left,right) = split (fn (key2,_) => +let partionLt compare tree key = + let comparator (key2, _) = match compare key key2 with - | Less => Less - | _ => Greater - end) tree - in - (left, right) - -let partionGt compare tree key = - let (_,left,right) = split (fn (key2,_) => + | Lt => Lt + | _ => Gt + end + let (_,left,right) = split comparator tree in + (left, right) + +let partionGt compare tree key = + let comparator (key2, _) = match compare key key2 with - | Greater => Greater - | _ => Less - end) tree - in - (left, right) - -let rec lowerBound tree = - match tree with - | Leaf => None - | Node {left = Leaf, value} => Some value - | Node {left} => lowerBound left + | Gt => Gt + | _ => Lt + end + let (_,left,right) = split comparator tree in + (left, right) + +let rec lowerBound tree = + match tree with + | Leaf => None + | Node {left = Leaf, value} => Some value + | Node {left} => lowerBound left end let lowerBoundErr tree = @@ -369,11 +409,11 @@ let lowerBoundErr tree = | Some x => x end -let rec upperBound tree = - match tree with - | Leaf => None - | Node { value, right=Leaf} => Some value - | Node {right} => upperBound right +let rec upperBound tree = + match tree with + | Leaf => None + | Node {value, right=Leaf} => Some value + | Node {right} => upperBound right end let upperBoundErr tree = @@ -382,18 +422,18 @@ let upperBoundErr tree = | Some x => x end -let rec lowerBoundGt compare tree key = +let rec lowerBoundGt compare tree key = match tree with - | Leaf => None - | Node {left, value = (key1, value), right} => - match compare key key1 with - | Less => - match lowerBoundGt compare left key with - | None => Some (key1, value) - | x => x - end - | Equal => lowerBound right - | Greater => lowerBoundGt compare right key + | Leaf => None + | Node {left, value = (key1, value), right} => + match compare key key1 with + | Lt => + match lowerBoundGt compare left key with + | None => Some (key1, value) + | x => x + end + | Eq => lowerBound right + | Gt => lowerBoundGt compare right key end end @@ -404,17 +444,17 @@ let lowerBoundGtErr compare tree key = end let rec lowerBoundGeq compare tree key = - match tree with - | Leaf => None - | Node {left, value = (key1, value), right} => - match compare key key1 with - | Less => - match lowerBoundGeq compare left key with - | None => Some (key1,value) - | x => x - end - | Equal => Some (key1, value) - | Greater => lowerBoundGeq compare right key + match tree with + | Leaf => None + | Node {left, value = (key1, value), right} => + match compare key key1 with + | Lt => + match lowerBoundGeq compare left key with + | None => Some (key1,value) + | x => x + end + | Eq => Some (key1, value) + | Gt => lowerBoundGeq compare right key end end @@ -424,43 +464,43 @@ let lowerBoundGeqErr compare tree key = | Some x => x end -let rec upperBoundLt compare tree key = +let rec upperBoundLt compare tree key = match tree with - | Leaf => None - | Node {left, value = (key1,value), right} => - match compare key key1 with - | Less => upperBoundLt compare left key - | Equal => upperBound left - | Greater => - match upperBoundLt compare right key with - | None => Some (key1,value) - | x => x - end + | Leaf => None + | Node {left, value = (key1,value), right} => + match compare key key1 with + | Lt => upperBoundLt compare left key + | Eq => upperBound left + | Gt => + match upperBoundLt compare right key with + | None => Some (key1,value) + | x => x end + end end -let upperBoundLtErr compare tree key = - match upperBoundLt compare tree key with +let upperBoundLtErr compare tree key = + match upperBoundLt compare tree key with | None => ~onError () | Some x => x end let rec upperBoundLeq compare tree key = - match tree with - | Leaf => None - | Node {left, value = (key1,value), right} => - match compare key key1 with - | Less => upperBoundLt compare left key - | Equal => Some (key1,value) - | Greater => - match upperBoundLeq compare right key with - | None => Some (key1,value) - | x => x - end + match tree with + | Leaf => None + | Node {left, value = (key1,value), right} => + match compare key key1 with + | Lt => upperBoundLt compare left key + | Eq => Some (key1,value) + | Gt => + match upperBoundLeq compare right key with + | None => Some (key1,value) + | x => x end + end end -let upperBoundLeqErr compare tree key = +let upperBoundLeqErr compare tree key = match upperBoundLeq compare tree key with | None => ~onError () | Some x => x @@ -473,37 +513,12 @@ let toValueList tree = foldr (fn key value acc => value :: acc) tree [] let domain tree = foldr (fn key value acc => key :: acc) tree [] let partion compare tree key = - let (output,left,right) = split (fn (key2,_) => compare key key2) tree - in - match output with - | None => (left,None,right) - | Some (_,x) => (left,Some x, right) + let (output,left,right) = split (keyComp compare key) tree in + match output with + | None => (left,None,right) + | Some (_,x) => (left,Some x, right) end -let _range compare tree left right = - match (left,right) with - | (Inclusion left, Inclusion right) => - let (_,middle) = partionGt compare tree left in - let (result,_) = partionLt compare middle right in result - | (Inclusion left, Exclusion right) => - let (_,middle) = partionGt compare tree left in - let (result,_) = partionGt compare middle right in result - | (Exclusion left, Inclusion right) => - let (_,middle) = partionLt compare tree left in - let (result,_) = partionLt compare middle right in result - | (Exclusion left, Exclusion right) => - let (_,middle) = partionLt compare tree left in - let (result,_) = partionGt compare middle right in result - end - -let range compare tree incl left incr right = - match (incl,incr) with - | (False,False) => _range compare tree (Exclusion left) (Exclusion right) - | (False,True) => _range compare tree (Exclusion left) (Inclusion right) - | (True,False) => _range compare tree (Inclusion left) (Exclusion right) - | (True,True) => _range compare tree (Inclusion left) (Inclusion right) - end - data MapT Key Val = MapT of Tree (Pair Key Val) # Wrappers @@ -511,21 +526,21 @@ let isEmptyT (MapT tree) = isEmpty tree let insertT compare (MapT tree) key val = MapT (insert compare tree key val) -let insertChangeT compare (MapT tree) key val = +let insertChangeT compare (MapT tree) key val = let (tree,bool) = insert' compare tree key val in (MapT tree, bool) let removeT compare (MapT tree) key = MapT (remove compare tree key) -let removeChangeT compare (MapT tree) key = +let removeChangeT compare (MapT tree) key = let (tree,bool) = remove' compare tree key in (MapT tree, bool) let memberT compare (MapT tree) key = member compare tree key let findT compare (MapT tree) key = find compare tree key -let operateT compare (MapT tree) key absentf presentf = - let (val,res,tree) = operate compare tree key absentf presentf - in (val,res, MapT tree) +let findErrT compare (MapT tree) key = findErr compare tree key + +let updateT compare (MapT tree) key f = MapT (update compare tree key f) let mapFoldl (MapT tree) func acc = foldl func tree acc @@ -541,25 +556,19 @@ let mapVal (MapT tree) func = MapT (map tree func) let mapKey (MapT tree) func = MapT (map2 tree func) -let appT (MapT tree) func = app tree func +let iterT (MapT tree) func = iter tree func -let unionT compare (MapT tree1) (MapT tree2) merge = +let unionT compare (MapT tree1) (MapT tree2) merge = MapT (union compare tree1 tree2 merge) -let partionT compare (MapT tree) key = - let (t1,v,t2) = partion compare tree key - in (MapT t1, v, MapT t2) - -let partionLtT compare (MapT tree) key = - let (t1,t2) = partionLt compare tree key - in (MapT t1, MapT t2) +let partionT compare (MapT tree) key = + let (t1,v,t2) = partion compare tree key in (MapT t1, v, MapT t2) -let partionGtT compare (MapT tree) key = - let (t1,t2) = partionGt compare tree key - in (MapT t1, MapT t2) +let partionLtT compare (MapT tree) key = + let (t1,t2) = partionLt compare tree key in (MapT t1, MapT t2) -let rangeT compare (MapT tree) incl left incr right = - MapT (range compare tree incl left incr right) +let partionGtT compare (MapT tree) key = + let (t1,t2) = partionGt compare tree key in (MapT t1, MapT t2) let lowerBoundT (MapT tree) = lowerBound tree @@ -571,13 +580,11 @@ let upperBoundTErr (MapT tree) = upperBoundErr tree let lowerBoundGtT compare (MapT tree) key = lowerBoundGt compare tree key -let lowerBoundGtTErr compare (MapT tree) key = - lowerBoundGtErr compare tree key +let lowerBoundGtTErr compare (MapT tree) key = lowerBoundGtErr compare tree key let upperBoundLtT compare (MapT tree) key = upperBoundLt compare tree key -let upperBoundLtTErr compare (MapT tree) key = - upperBoundLtErr compare tree key +let upperBoundLtTErr compare (MapT tree) key = upperBoundLtErr compare tree key let lowerBoundGeqT compare (MapT tree) key = lowerBoundGeq compare tree key @@ -586,10 +593,10 @@ let lowerBoundGeqTErr compare (MapT tree) key = let upperBoundLeqT compare (MapT tree) key = upperBoundLeq compare tree key -let upperBoundLeqTErr compare (MapT tree) key = +let upperBoundLeqTErr compare (MapT tree) key = upperBoundLeqErr compare tree key -pub let make {Key} (compare : Key -> Key -> [] Ordered) = Map { +pub let make {Key} (compare : Key -> Key ->[] Ordered) = Map { T = MapT Key , empty = MapT Leaf , method isEmpty = isEmptyT @@ -599,7 +606,8 @@ pub let make {Key} (compare : Key -> Key -> [] Ordered) = Map { , method removeChange = removeChangeT compare , method member = memberT compare , method find = findT compare - , method operate = operateT compare + , method findErr = findErrT compare + , method update = updateT compare , method foldl = mapFoldl , method foldr = mapFoldr , method toList = toListT @@ -607,12 +615,11 @@ pub let make {Key} (compare : Key -> Key -> [] Ordered) = Map { , method domain = domainT , method mapVal = mapVal , method mapKey = mapKey - , method app = appT + , method iter = iterT , method union = unionT compare , method partion = partionT compare , method partionLt = partionLtT compare , method partionGt = partionGtT compare - , method range = rangeT compare , method lowerBound = lowerBoundT , method lowerBoundErr = lowerBoundTErr , method upperBound = upperBoundT diff --git a/lib/Prelude.fram b/lib/Prelude.fram index a41ab52f..3817a5e3 100755 --- a/lib/Prelude.fram +++ b/lib/Prelude.fram @@ -47,7 +47,3 @@ pub module Int64 pub let ofInt (n : Int) = n.toInt64 end -pub data Ordered = -| Less -| Equal -| Greater diff --git a/lib/Queue.fram b/lib/Queue.fram index df120021..bc9ec0b5 100755 --- a/lib/Queue.fram +++ b/lib/Queue.fram @@ -6,31 +6,31 @@ import List data NotNegativeInt = Zero | Positive of Int -let addOne value = +let addOne value = match value with - | Zero => Positive 1 - | Positive n => Positive (n+1) + | Zero => Positive 1 + | Positive n => Positive (n+1) end -let subOne value = +let subOne value = match value with | Zero => Zero | Positive n => if n == 1 then Zero else Positive (n-1) end -data RotationState Val = +data RotationState Val = | Idle | Reversing of NotNegativeInt, List Val, List Val, List Val, List Val | Appending of NotNegativeInt, List Val, List Val | Done of List Val -data HoodMelvilleQueue Val = +data HoodMelvilleQueue Val = | HMQueue of NotNegativeInt, List Val, RotationState Val, NotNegativeInt, List Val -let exec state = - match state with - | Reversing ok (x::f) f' (y::r) r' => +let exec state = + match state with + | Reversing ok (x::f) f' (y::r) r' => Reversing (addOne ok) f (x::f') r (y::r') | Reversing ok [] f' [y] r' => Appending ok f' (y::r') | Appending Zero f' r' => Done r' @@ -48,14 +48,14 @@ let invalidate state = let exec_twice hmqueue = match hmqueue with - | HMQueue lenf f state lenr r => + | HMQueue lenf f state lenr r => match exec (exec state) with | Done newf => HMQueue lenf newf Idle lenr r | newstate => HMQueue lenf f newstate lenr r end end -let leq v1 v2 = +let leq v1 v2 = match (v1,v2) with | (Zero,Zero) => True | (Zero,Positive _) => True @@ -63,7 +63,7 @@ let leq v1 v2 = | (Positive n, Positive m) => n <= m end -let add v1 v2 = +let add v1 v2 = match (v1,v2) with | (Zero,any) => any | (any,Zero) => any @@ -72,29 +72,29 @@ let add v1 v2 = let check queue = match queue with - | HMQueue lenf f state lenr r => + | HMQueue lenf f state lenr r => if leq lenr lenf then exec_twice queue else ( let newstate = Reversing Zero f [] r [] in - exec_twice (HMQueue (add lenf lenr) f newstate Zero []) + exec_twice (HMQueue (add lenf lenr) f newstate Zero []) ) end pub let emptyQueue = HMQueue Zero [] Idle Zero [] -pub let isEmpty queue = - match queue with +pub let isEmpty queue = + match queue with | HMQueue Zero _ _ _ _ => True | _ => False end let snoc queue value = match queue with - | HMQueue lenf f state lenr r => - check (HMQueue lenf f state (addOne lenr) (value :: r)) + | HMQueue lenf f state lenr r => + check (HMQueue lenf f state (addOne lenr) (value :: r)) end let head queue = - match queue with + match queue with | HMQueue Zero _ _ _ _ => None | HMQueue _ (x::xs) _ _ _ => Some x | _ => impossible () @@ -104,38 +104,35 @@ let tail queue = match queue with | HMQueue Zero _ _ _ _ => emptyQueue | HMQueue _ [] _ _ _ => emptyQueue - | HMQueue lenf (x::xs) state lenr r => - check (HMQueue (subOne lenf) xs (invalidate state) lenr r) + | HMQueue lenf (x::xs) state lenr r => + check (HMQueue (subOne lenf) xs (invalidate state) lenr r) end -let foldlRotationState f acc state = +let foldlRotationState f acc state = match state with | Idle => acc | Done list => List.foldLeft f acc list - | Appending _ list1 list2 => - List.foldLeft f - (List.foldLeft f acc list2) + | Appending _ list1 list2 => + List.foldLeft f + (List.foldLeft f acc list2) list1 - | Reversing _ list1 list2 list3 list4 => - List.foldLeft f - (List.foldLeft f - (List.foldLeft f + | Reversing _ list1 list2 list3 list4 => + List.foldLeft f + (List.foldLeft f + (List.foldLeft f (List.foldLeft f acc list4) - list3 - ) - list2 - ) + list3) + list2) list1 end pub let foldlQueue queue f acc = match queue with | HMQueue _ list1 state _ list2 => - List.foldLeft f + List.foldLeft f (foldlRotationState f - (List.foldLeft f acc list1) - state - ) + (List.foldLeft f acc list1) + state) list2 end @@ -150,16 +147,15 @@ let mapRotationState f state = (List.map f list3) (List.map f list4) end -let mapQueue queue f = +let mapQueue queue f = match queue with | HMQueue v1 list1 state v2 list2 => - HMQueue v1 (List.map f list1) - (mapRotationState f state) v2 - (List.map f list2) + HMQueue v1 (List.map f list1) + (mapRotationState f state) v2 (List.map f list2) end -let rec toList queue = - match head queue with +let rec toList queue = + match head queue with | None => [] | Some x => x :: toList (tail queue) end diff --git a/lib/RedBlackTree.fram b/lib/RedBlackTree.fram index 190fd4f3..3f81f758 100755 --- a/lib/RedBlackTree.fram +++ b/lib/RedBlackTree.fram @@ -6,16 +6,10 @@ #import open Base/Assert import List -pub data Comparable = Eq| Noteq - -pub let ordToComp elem = match elem with | Equal => Eq | _ => Noteq end - -pub method toComparable {self : Ordered} = ordToComp self - data Color = - | Red + | Red | Black -pub data rec Tree Value = +pub data rec Tree Value = | Leaf | Node of { color: Color, @@ -26,104 +20,100 @@ pub data rec Tree Value = } data ZipElem Value = | Left of Color, Value, Tree Value - | Right of Color, Tree Value, Value + | Right of Color, Tree Value, Value pub let empty = Leaf -pub let size tree = +pub let size tree = match tree with - | Leaf => 0 - | Node {size} => size + | Leaf => 0 + | Node {size} => size end -pub let makeNode color left value right = +pub let makeNode color left value right = Node {color, size = size left + size right + 1, left, value, right} -pub let construct color size left value right = +pub let construct color size left value right = Node {color,size,left,value,right} pub let rec zip tree zipper = match zipper with | [] => tree - | Left color value right :: rest => - zip (makeNode color tree value right) rest + | Left color value right :: rest => + zip (makeNode color tree value right) rest - | Right color left value :: rest => - zip (makeNode color left value tree) rest + | Right color left value :: rest => + zip (makeNode color left value tree) rest end pub let rec zipRed value left right zipper = match zipper with - |[] => makeNode Black left value right + | [] => makeNode Black left value right - |Left Black value1 right1 :: rest => - zip (makeNode Black (makeNode Red left value right) value1 right1) rest + | Left Black value1 right1 :: rest => + zip (makeNode Black (makeNode Red left value right) value1 right1) rest - | Right Black left1 value1 :: rest => - zip (makeNode Black left1 value1 (makeNode Red left value right)) rest - - | Left Red value1 right1 :: - Left _ value2 - (Node {color = Red, size = bulk3, left = left3, - value = value3, right = right3}) :: rest => - zipRed value2 - (makeNode Black (makeNode Red left value right) value1 right1) - (construct Black bulk3 left3 value3 right3) rest - - | Left Red value1 right1 :: - Right _ - (Node {color = Red, size = bulk3, left = left3, - value = value3, right = right3}) value2 :: rest => - zipRed value2 - (construct Black bulk3 left3 value3 right3) - (makeNode Black (makeNode Red left value right) value1 right1) rest - - | Right Red left1 value1 :: - Left _ value2 - (Node {color = Red, size = bulk3, left = left3, - value = value3, right = right3}) :: rest => - zipRed value2 - (makeNode Black left1 value1 (makeNode Red left value right)) - (construct Black bulk3 left3 value3 right3) rest - - | Right Red left1 value1 :: - Right _ (Node {color = Red, size = bulk3, left = left3, - value = value3, right = right3}) value2 :: rest => - zipRed value2 - (construct Black bulk3 left3 value3 right3) - (makeNode Black left1 value1 (makeNode Red left value right)) rest + | Right Black left1 value1 :: rest => + zip (makeNode Black left1 value1 (makeNode Red left value right)) rest | Left Red value1 right1 :: - Left _ value2 node3 :: rest => - zip - (makeNode Black (makeNode Red left value right) value1 - (makeNode Red right1 value2 node3)) rest + Left _ value2 + (Node {color = Red, size = size3, left = left3, + value = value3, right = right3}) :: rest => + let left' = makeNode Red left value right + let right' = construct Black size3 left3 value3 right3 in + zipRed value2 (makeNode Black left' value1 right1) right' rest | Left Red value1 right1 :: - Right _ node3 value2 :: rest => - zip - (makeNode Black (makeNode Red node3 value2 left) - value (makeNode Red right value1 right1)) rest + Right _ + (Node {color = Red, size = size3, left = left3, + value = value3, right = right3}) value2 :: rest => + let left' = construct Black size3 left3 value3 right3 + let right' = makeNode Red left value right in + zipRed value2 left' (makeNode Black right' value1 right1) rest | Right Red left1 value1 :: - Left _ value2 node3 :: rest => - zip - (makeNode Black (makeNode Red left1 value1 left) - value (makeNode Red right value2 node3)) rest + Left _ value2 + (Node {color = Red, size = size3, left = left3, + value = value3, right = right3}) :: rest => + let left' = makeNode Red left value right + let right' = construct Black size3 left3 value3 right3 in + zipRed value2 (makeNode Black left1 value1 left') right' rest | Right Red left1 value1 :: - Right _ node3 value2 :: rest => - zip - (makeNode Black (makeNode Red node3 value2 left1) - value1 (makeNode Red left value right)) rest - - | Left Red value1 right1 :: - [] => makeNode Black (makeNode Red left value right) value1 right1 - - | Right Red left1 value1 :: - [] => makeNode Black left1 value1 (makeNode Red left value right) + Right _ (Node {color = Red, size = size3, left = left3, + value = value3, right = right3}) value2 :: rest => + let left' = construct Black size3 left3 value3 right3 + let right' = makeNode Red left value right in + zipRed value2 left' (makeNode Black left1 value1 right') rest + + | Left Red value1 right1 :: Left _ value2 node3 :: rest => + let left' = makeNode Red left value right + let right' = makeNode Red right1 value2 node3 in + zip (makeNode Black left' value1 right') rest + + | Left Red value1 right1 :: Right _ node3 value2 :: rest => + let left' = makeNode Red node3 value2 left + let right' = makeNode Red right value1 right1 in + zip (makeNode Black left' value right') rest + + | Right Red left1 value1 :: Left _ value2 node3 :: rest => + let left' = makeNode Red left1 value1 left + let right' = makeNode Red right value2 node3 in + zip (makeNode Black left' value right') rest + + | Right Red left1 value1 :: Right _ node3 value2 :: rest => + let left' = makeNode Red node3 value2 left1 + let right' = makeNode Red left value right in + zip (makeNode Black left' value1 right') rest + + | Left Red value1 right1 :: [] => + makeNode Black (makeNode Red left value right) value1 right1 + + | Right Red left1 value1 :: [] => + makeNode Black left1 value1 (makeNode Red left value right) end @@ -131,64 +121,65 @@ pub let rec zipBlack tree zipper = match zipper with | [] => tree - | Left color1 value1 - (Node {left = left2, value = value2, - right = (Node {color = Red, size = bulk3, - left = left3, value = value3, right = right3})}) :: - rest => - zip - (makeNode color1 (makeNode Black tree value1 left2 ) value2 - (construct Black bulk3 left3 value3 right3)) rest - - | Right color1 (Node { left = (Node {color = Red, size = bulk3, left = left3, - value = value3, right = right3}), value = value2, right = right2}) - value1 :: rest => - zip - (makeNode color1 (construct Black bulk3 left3 value3 right3) value2 - (makeNode Black right2 value1 tree)) rest - - | Left color1 value1 (Node {left = (Node {color = Red, left = left3, - value = value3, right = right3}), value = value2, right = right2}) :: rest => - zip - (makeNode color1 (makeNode Black tree value1 left3) value3 - (makeNode Black right3 value2 right2)) rest - - | Right color1 (Node {left = left2, value = value2, right = - (Node {color = Red,left = left3, value = value3, right = right3})}) - value1 :: rest => - zip (makeNode color1 (makeNode Black left2 value2 left3) - value3 (makeNode Black right3 value1 tree)) rest - - | Left Red value1 (Node {size = bulk2, left = left2, - value = value2, right=right2}) :: rest => - zip - (makeNode Black tree value1 (construct Red bulk2 left2 value2 right2)) rest - - | Right Red (Node {size = bulk2, left = left2, - value = value2, right = right2}) value1 :: rest => - zip - (makeNode Black (construct Red bulk2 left2 value2 right2) value1 tree) rest - - | Left Black value1 (Node {color = Black, size = bulk2, left = left2, - value = value2,right = right2}) :: rest => - zipBlack - (makeNode Black tree value1 (construct Red bulk2 left2 value2 right2)) rest - - | Right Black (Node {color = Black, size = bulk2, left = left2, - value = value2, right = right2}) value1 :: rest => - zipBlack - (makeNode Black (construct Red bulk2 left2 value2 right2) value1 tree) rest + | Left color1 value1 + (Node {left = left2, value = value2, + right = (Node {color = Red, size = size3, + left = left3, value = value3, right = right3})}) :: + rest => + let left' = makeNode Black tree value1 left2 + let right' = construct Black size3 left3 value3 right3 in + zip (makeNode color1 left' value2 right') rest + + | Right color1 (Node { left = (Node {color = Red, size = size3, left = left3, + value = value3, right = right3}), value = value2, right = right2}) + value1 :: rest => + let left' = construct Black size3 left3 value3 right3 + let right' = makeNode Black right2 value1 tree in + zip (makeNode color1 left' value2 right') rest + + | Left color1 value1 (Node {left = (Node {color = Red, left = left3, + value = value3, right = right3}), + value = value2, right = right2}) :: rest => + let left' = makeNode Black tree value1 left3 + let right' = makeNode Black right3 value2 right2 in + zip (makeNode color1 left' value3 right') rest + + | Right color1 (Node {left = left2, value = value2, right = + (Node {color = Red, left = left3, value = value3, right = right3})}) + value1 :: rest => + let left' = makeNode Black left2 value2 left3 + let right' = makeNode Black right3 value1 tree in + zip (makeNode color1 left' value3 right') rest + + | Left Red value1 (Node {size = size2, left = left2, + value = value2, right = right2}) :: rest => + let right' = construct Red size2 left2 value2 right2 in + zip (makeNode Black tree value1 right') rest + + | Right Red (Node {size = size2, left = left2, + value = value2, right = right2}) value1 :: rest => + let left' = construct Red size2 left2 value2 right2 in + zip (makeNode Black left' value1 tree) rest + + | Left Black value1 (Node {color = Black, size = size2, left = left2, + value = value2, right = right2}) :: rest => + let right' = construct Red size2 left2 value2 right2 in + zipBlack (makeNode Black tree value1 right') rest + + | Right Black (Node {color = Black, size = size2, left = left2, + value = value2, right = right2}) value1 :: rest => + let left' = construct Red size2 left2 value2 right2 in + zipBlack (makeNode Black left' value1 tree) rest | Left Black value1 (Node {color = Red, left = left2, - value = value2, right = right2}) :: rest => - zipBlack - tree (Left Red value1 left2 :: Left Black value2 right2 :: rest) - - | Right Black (Node {color = Red, left = left2, value = value2, - right = right2}) value1 :: rest => - zipBlack - tree (Right Red right2 value1 :: Right Black left2 value2 :: rest) - + value = value2, right = right2}) :: rest => + zipBlack tree (Left Red value1 left2 :: Left Black value2 right2 :: rest) + + | Right Black (Node {color = Red, left = left2, value = value2, + right = right2}) value1 :: rest => + let rest' = Right Red right2 value1 :: Right Black left2 value2 :: rest in + zipBlack tree rest' + # Impossible | Left _ _ Leaf :: _ => impossible () @@ -196,72 +187,74 @@ pub let rec zipBlack tree zipper = end -pub let rec search func tree zipper = +pub let rec search func tree zipper = match tree with | Leaf => (Leaf, zipper) - | Node {color, size=_, left, value, right} => - match func value with - | Less => + | Node {color, left, value, right} => + match func value with + | Lt => search func left (Left color value right :: zipper) - | Greater => + | Gt => search func right (Right color left value :: zipper) - | Equal => (tree, zipper) + | Eq => (tree, zipper) end end pub let rec searchMin tree zipper = match tree with | Leaf => zipper - | Node {color,size=_,left,value,right} => - searchMin left (Left color value right :: zipper) + | Node {color, left, value, right} => + searchMin left (Left color value right :: zipper) end pub let rec searchMax tree zipper = match tree with - | Leaf => zipper - | Node {color,size=_, left, value, right} => - searchMax right (Right color left value:: zipper) + | Leaf => zipper + | Node {color, left, value, right} => + searchMax right (Right color left value:: zipper) end pub let deleteNearLeaf color child zipper = match color with | Red => zip Leaf zipper - | Black => match child with - | Node {value} => - zip (makeNode Black Leaf value Leaf) zipper + | Black => + match child with + | Node {value} => + zip (makeNode Black Leaf value Leaf) zipper | Leaf => zipBlack Leaf zipper end end pub let delete color left right zipper = match right with - | Leaf => + | Leaf => match left with - | Leaf => match color with + | Leaf => + match color with | Red => zip Leaf zipper | Black => zipBlack Leaf zipper end - | _ => + | _ => match searchMax left [] with - | Right colorLeftMin leftLeftMin valueLeftMin :: zipperr => - deleteNearLeaf colorLeftMin leftLeftMin - (List.append zipperr (Left color valueLeftMin right :: zipper)) + | Right colorLeftMin leftLeftMin valueLeftMin :: zipperr => + deleteNearLeaf colorLeftMin leftLeftMin + (List.append zipperr (Left color valueLeftMin right :: zipper)) | _ => Leaf end end - | _ => + | _ => match searchMin right [] with - | Left colorRightMin valueRightMin rightRightMin :: zipperr => - deleteNearLeaf colorRightMin rightRightMin - (List.append zipperr (Right color left valueRightMin :: zipper)) + | Left colorRightMin valueRightMin rightRightMin :: zipperr => + deleteNearLeaf colorRightMin rightRightMin + (List.append zipperr (Right color left valueRightMin :: zipper)) | _ => Leaf end end pub let blacken tree = match tree with - | Node {color=Red,size=bulk,left,value,right} => - construct Black bulk left value right + | Node {color = Red, size, left, value, right} => + construct Black size left value right | _ => tree end @@ -275,18 +268,20 @@ pub let rec blackHeight tree acc = pub let rec searchHeight leftward target tree zipper = match tree with | Leaf => (Leaf, zipper) - | Node {color=Red,left,value,right} => - if leftward then - searchHeight leftward target left (Left Red value right :: zipper) - else - searchHeight leftward target right (Right Red left value :: zipper) - | Node {color=Black,left,value,right} => - if 0 == target then - (tree,zipper) + | Node {color=Red,left,value,right} => + if leftward then + searchHeight leftward target left (Left Red value right :: zipper) + else + searchHeight leftward target right (Right Red left value :: zipper) + | Node {color=Black,left,value,right} => + if 0 == target then + (tree,zipper) else if leftward then - searchHeight leftward (target - 1) left (Left Black value right :: zipper) - else - searchHeight leftward (target - 1) right (Right Black left value :: zipper) + searchHeight leftward (target - 1) left + (Left Black value right :: zipper) + else + searchHeight leftward (target - 1) right + (Right Black left value :: zipper) end pub let joinVal left value right = @@ -294,24 +289,24 @@ pub let joinVal left value right = let right = blacken right in let lbh = blackHeight left 0 in let rbh = blackHeight right 0 in - if lbh == rbh then + if lbh == rbh then makeNode Black left value right else if lbh > rbh then (let (_left, zipper) = searchHeight False (lbh-rbh) left [] in zipRed value _left right zipper) - else + else (let (_right, zipper) = searchHeight True (rbh-lbh) right [] in zipRed value left _right zipper) pub let join left right = match left with | Leaf => right - | _ => + | _ => match right with | Leaf => left - | _ => + | _ => match searchMax left [] with - | Right color leftSmall value :: zipper => + | Right color leftSmall value :: zipper => joinVal (deleteNearLeaf color leftSmall zipper) value right |_ => left end @@ -321,13 +316,13 @@ pub let join left right = pub let rec split compareWithPivot tree = match tree with | Leaf => (None,Leaf,Leaf) - | Node {left,value,right} => + | Node {left,value,right} => match compareWithPivot value with - | Equal => (Some value, left, right) - | Less => + | Eq => (Some value, left, right) + | Lt => let (_v, _l, _r) = split compareWithPivot left in (_v, _l, joinVal _r value right) - | Greater => let (_v, _l, _r) = split compareWithPivot right in + | Gt => let (_v, _l, _r) = split compareWithPivot right in (_v, joinVal left value _l, _r) end end diff --git a/lib/Set.fram b/lib/Set.fram index 0e1af613..9cca9a64 100755 --- a/lib/Set.fram +++ b/lib/Set.fram @@ -13,247 +13,260 @@ data Interval Value = Inclusion of Value | Exclusion of Value pub data Set Elem = Set of { T - {# @brief Creates empty set - #} + + {## @brief Creates empty set + ##} , empty : T - {# @brief Method to testing whether given set is empty or not - # @return True if it's empty false otherwise - #} - , method isEmpty : T -> [] Bool - {# @brief Method for inserting element to the set + + {## @brief Method to testing whether given set is empty or not + # @return True if it's empty False otherwise + ##} + , method isEmpty : T ->[] Bool + + {## @brief Method for inserting element to the set # @param Element which will be inserted to the set # @return Set with inserted value - #} - , method insert : T -> Elem -> [] T - {# @brief Method for removig element from the set + ##} + , method insert : T -> Elem ->[] T + + {## @brief Method for removing element from the set # @param Element which will be removed # @return Set with removed element - #} - , method remove : T -> Elem -> [] T - {# @brief Method to test whether given element is in a given set or not + ##} + , method remove : T -> Elem ->[] T + + {## @brief Method to test whether given element is in a given set or not # @param Element which will be searched # @return True if given element is in given set, false otherwise - #} - , method member : T -> Elem -> [] Bool - {# @brief Method to fold left through structure of set + ##} + , method member : T -> Elem ->[] Bool + + {## @brief Method to fold left through structure of set # @param Function that receives element and accumulator # @param Accumulator # @return Result of applying function on elements of set and accumulator - #} - , method foldl : {type A,E} -> T -> (Elem -> A -> [|E] A) -> A -> [|E] A - {# @brief Method to fold right through structure of set + ##} + , method foldl : {type A,E} -> T -> (Elem -> A ->[|E] A) -> A ->[|E] A + + {## @brief Method to fold right through structure of set # @param Function that receives element and accumulator # @param Accumulator # @return Result of applying function on elements of set and accumulator - #} - , method foldr : {type A,E} -> T -> (Elem -> A -> [|E] A) -> A -> [|E] A - {# @brief Method to convert set to list of elements - #} - , method toList : T -> [] List Elem - {# @brief Method to create union of two sets + ##} + , method foldr : {type A,E} -> T -> (Elem -> A ->[|E] A) -> A ->[|E] A + + {## @brief Method to convert set to list of elements + ##} + , method toList : T ->[] List Elem + + {## @brief Method to create union of two sets # @param Set # @return Union of two sets - #} - , method union : T -> T -> [] T - {# @brief Method to create intersection of two sets + ##} + , method union : T -> T ->[] T + + {## @brief Method to create intersection of two sets # @param Set # @return Intersection of two sets - #} - , method intersection : T -> T -> [] T - {# @brief Method to create difference of two sets + ##} + , method intersection : T -> T ->[] T + + {## @brief Method to create difference of two sets # @param Set # @return Difference of two sets - #} - , method difference : T -> T -> [] T - {# @brief Method to check if two sets are equal + ##} + , method difference : T -> T ->[] T + + {## @brief Method to check if two sets are equal # @param Set # @return True if two sets are equal, false otherwise. - #} - , method eq : T -> T -> [] Bool - {# @brief Method to check if set which called this method is + ##} + , method eq : T -> T ->[] Bool + + {## @brief Method to check if set which called this method is # subset of a given set # @param Set # @return True if set is subset, false otherwise. - #} - , method subset : T -> T -> [] Bool - {# @brief Split set to two sets one containing elements - # lesser then given element, second one containing equal or greater - # @param Elem - # @return Pair of sets with order and specification previously mentioned - #} - , method partionLt : T -> Elem -> [] (Pair T T) - {# @brief Split set to two sets one containing elements - # lesser or equal then given element, second one containing greater - # @param Elem - # @return Pair of sets with order and specification previously mentioned - #} - , method partionGt : T -> Elem -> [] (Pair T T) - {# @brief Method that gives a subset in a given range - # @param First Bool - if the subset should include lower element or not - # @param First Elem - lower value which all elements - # in returned set will be greater (or equal) - # @param Second Bool - if the subset should include upper element or not - # @param Second Elem - upper value which all elements in - # in returned set will be lower (or equal) - # @return Subset in a given range - #} - , method range : T -> Bool -> Elem -> Bool -> Elem -> [] T - {# @brief Method that returns lowest stored value in a set - # @return Some value if the smallest element exist or otherwise None - #} - , method lowerBound : T -> [] Option Elem - {# @brief Method that returns lowest stored value in a set - # @return smallest element or error - #} - , method lowerBoundErr : - {Err, ~onError : Unit -> [Err] Elem} -> T -> [Err] Elem - {# @brief Method that returns the greatest stored value in a set - # @return Some value if the greatest element exist or otherwise None - #} - , method upperBound : T -> [] Option Elem - {# @brief Method that returns the greatest stored value in a set - # @return greatest element or error - #} - , method upperBoundErr : - {Err, ~onError : Unit -> [Err] Elem} -> T -> [Err] Elem - {# @brief Method that returns the lowest element greater than given element - # @return Some value or None - #} - , method lowerBoundGt : T -> Elem -> [] Option Elem - {# @brief Method that returns the lowest element greater than given element - # @return value or error - #} - , method lowerBoundGtErr : - {Err, ~onError : Unit -> [Err] Elem} -> T -> Elem -> [Err] Elem - {# @brief Method that returns the lowest element greater - # or equal than given element - # @return Some value or None - #} - , method lowerBoundGeq : T -> Elem -> [] Option Elem - {# @brief Method that returns the lowest element greater - # or equal than given element - # @return value or error - #} + ##} + , method subset : T -> T ->[] Bool + + {## @brief Split set to two sets one containing elements + # lesser then given element, second one containing equal or greater + # @param Elem + # @return Pair of sets with order and specification previously mentioned + ##} + , method partionLt : T -> Elem ->[] (Pair T T) + + {## @brief Split set to two sets one containing elements + # lesser or equal then given element, second one containing greater + # @param Elem + # @return Pair of sets with order and specification previously mentioned + ##} + , method partionGt : T -> Elem ->[] (Pair T T) + + {## @brief Method that returns lowest stored value in a set + # @return Some value if the smallest element exist or otherwise None + ##} + , method lowerBound : T ->[] Option Elem + + {## @brief Method that returns lowest stored value in a set + # @return smallest element or error + ##} + , method lowerBoundErr : + {Err, ~onError : Unit ->[Err] Elem} -> T ->[Err] Elem + + {## @brief Method that returns the greatest stored value in a set + # @return Some value if the greatest element exist or otherwise None + ##} + , method upperBound : T ->[] Option Elem + + {## @brief Method that returns the greatest stored value in a set + # @return greatest element or error + ##} + , method upperBoundErr : + {Err, ~onError : Unit ->[Err] Elem} -> T ->[Err] Elem + + {## @brief Method that returns the lowest element greater than given element + # @return Some value or None + ##} + , method lowerBoundGt : T -> Elem ->[] Option Elem + + {## @brief Method that returns the lowest element greater than given element + # @return value or error + ##} + , method lowerBoundGtErr : + {Err, ~onError : Unit ->[Err] Elem} -> T -> Elem ->[Err] Elem + + {## @brief Method that returns the lowest element greater + # or equal than given element + # @return Some value or None + ##} + , method lowerBoundGeq : T -> Elem ->[] Option Elem + + {## @brief Method that returns the lowest element greater + # or equal than given element + # @return value or error + ##} , method lowerBoundGeqErr : - {Err, ~onError : Unit -> [Err] Elem} -> T -> Elem -> [Err] Elem - {# @brief Method that returns the greatest element lower than given element - # @return Some value or None - #} - , method upperBoundLt : T -> Elem -> [] Option Elem - {# @brief Method that returns the greatest element lower than given element - # @return value or error - #} + {Err, ~onError : Unit ->[Err] Elem} -> T -> Elem ->[Err] Elem + + {## @brief Method that returns the greatest element lower than given element + # @return Some value or None + ##} + , method upperBoundLt : T -> Elem ->[] Option Elem + + {## @brief Method that returns the greatest element lower than given element + # @return value or error + ##} , method upperBoundLtErr : - {Err, ~onError : Unit -> [Err] Elem} -> T -> Elem -> [Err] Elem - {# @brief Method that returns the greatest element lower - # or equal than given element - # @return Some value or None - #} - , method upperBoundLeq : T -> Elem -> [] Option Elem - {# @brief Method that returns the greatest element lower - # or equal than given element - # @return value or error - #} + {Err, ~onError : Unit ->[Err] Elem} -> T -> Elem ->[Err] Elem + + {## @brief Method that returns the greatest element lower + # or equal than given element + # @return Some value or None + ##} + , method upperBoundLeq : T -> Elem ->[] Option Elem + + {## @brief Method that returns the greatest element lower + # or equal than given element + # @return value or error + ##} , method upperBoundLeqErr : - {Err, ~onError : Unit -> [Err] Elem} -> T -> Elem -> [Err] Elem + {Err, ~onError : Unit ->[Err] Elem} -> T -> Elem ->[Err] Elem } -# Red black tree implementation +# Red black tree implementation -data rec Q Val = Nil | E of Val , Q Val | T of Tree Val , Q Val +data rec Q Val = Nil | E of Val, Q Val | T of Tree Val, Q Val -let rec eqMain eq qs1 qs2 = +let rec eqMain compare qs1 qs2 = match (qs1,qs2) with - | (Nil,Nil) => True + | (Nil,Nil) => True + + | (Nil, E _ _) => False - | (Nil, E _ _) => False + | (E _ _, Nil) => False - | (E _ _, Nil) => False + | (T Leaf rest, _) => eqMain compare rest qs2 - | (T Leaf rest, _) => eqMain eq rest qs2 + | (_, T Leaf rest) => eqMain compare qs1 rest - | (_, T Leaf rest) => eqMain eq qs1 rest + | (T (Node {left, value = elem, right}) rest, _) => + eqMain compare (T left (E elem (T right rest))) qs2 - | (T (Node {left, value = elem, right}) rest, _) => - eqMain eq (T left (E elem (T right rest))) qs2 - - | (_, T (Node {left, value = elem, right}) rest) => - eqMain eq qs1 (T left (E elem (T right rest))) - - | (E elem1 rest1, E elem2 rest2) => - match eq elem1 elem2 with - | Noteq => False - | Eq => eqMain eq rest1 rest2 - end + | (_, T (Node {left, value = elem, right}) rest) => + eqMain compare qs1 (T left (E elem (T right rest))) + + | (E elem1 rest1, E elem2 rest2) => + match compare elem1 elem2 with + | Eq => eqMain compare rest1 rest2 + | _ => False + end end -let rec subsetMain comp qs1 qs2 = +let rec subsetMain comp qs1 qs2 = match (qs1,qs2) with - | (Nil,_) => True - - | (E _ _ , Nil) => False - - | (T Leaf rest, _) => subsetMain comp rest qs2 - - | (_ , T Leaf rest) => subsetMain comp qs1 rest - - | (T (Node {left, value = elem, right}) rest, _) => - subsetMain comp (T left (E elem (T right rest))) qs2 - - | (_, T (Node {left, value = elem, right}) rest) => - subsetMain comp qs1 (T left (E elem (T right rest))) - - | (E elem1 rest1, E elem2 rest2) => - match comp elem1 elem2 with - | Less => False - | Equal => subsetMain comp rest1 rest2 - | Greater => subsetMain comp qs1 rest2 - end + | (Nil,_) => True + + | (E _ _ , Nil) => False + + | (T Leaf rest, _) => subsetMain comp rest qs2 + + | (_ , T Leaf rest) => subsetMain comp qs1 rest + + | (T (Node {left, value = elem, right}) rest, _) => + subsetMain comp (T left (E elem (T right rest))) qs2 + + | (_, T (Node {left, value = elem, right}) rest) => + subsetMain comp qs1 (T left (E elem (T right rest))) + + | (E elem1 rest1, E elem2 rest2) => + match comp elem1 elem2 with + | Lt => False + | Eq => subsetMain comp rest1 rest2 + | Gt => subsetMain comp qs1 rest2 + end end -let partionLt compare = fn tree key1 => - let (_,left,right) = - split - (fn key2 => - match compare key1 key2 with - | Greater => Greater - | _ => Less - end) - tree - in (left,right) - -let partionGt compare = fn tree key1 => - let (_, left,right) = - split - (fn key2 => - match compare key1 key2 with - | Less => Less - | _ => Greater - end) - tree - in (left,right) - -let rec least tree = - match tree with - | Leaf => None - | Node {left = Leaf, value = x} => Some x - | Node {left} => least left +let partionLt compare tree key1 = + let comparator key2 = + match compare key1 key2 with + | Gt => Gt + | _ => Lt + end + let (_,left,right) = split comparator tree in + (left,right) + +let partionGt compare tree key1 = + let comparator key2 = + match compare key1 key2 with + | Lt => Lt + | _ => Gt + end + let (_, left,right) = split comparator tree in + (left,right) + +let rec least tree = + match tree with + | Leaf => None + | Node {left = Leaf, value} => Some value + | Node {left} => least left end let leastErr tree = match least tree with | None => ~onError () | Some x => x - end + end -let rec greatest tree = - match tree with - | Leaf => None - | Node {value = x, right = Leaf} => Some x - | Node {right} => greatest right +let rec greatest tree = + match tree with + | Leaf => None + | Node {value, right = Leaf} => Some value + | Node {right} => greatest right end -let greatestErr tree = +let greatestErr tree = match greatest tree with | None => ~onError () | Some x => x @@ -261,157 +274,137 @@ let greatestErr tree = let empty = Leaf -let isEmpty tree = - match tree with - | Leaf => True - | _ => False +let isEmpty tree = + match tree with + | Leaf => True + | _ => False end let rec member compare tree elem = match tree with - | Leaf => False - | Node {left, value, right} => - match compare elem value with - | Less => member compare left elem - | Greater => member compare right elem - | Equal => True - end + | Leaf => False + | Node {left, value, right} => + match compare elem value with + | Lt => member compare left elem + | Gt => member compare right elem + | Eq => True + end end - -let insert compare tree elem = - match search (fn val => compare elem val) tree [] with - | (Leaf,zipper) => zipRed elem Leaf Leaf zipper - | (Node ,_) => tree + +let insert compare tree elem = + match search (compare elem) tree [] with + | (Leaf,zipper) => zipRed elem Leaf Leaf zipper + | (Node ,_) => tree end -let remove compare tree elem = - match search (fn val => compare elem val) tree [] with - | (Leaf,_) => tree - | (Node {color, left, right},zipper) => delete color left right zipper - end +let remove compare tree elem = + match search (compare elem) tree [] with + | (Leaf, _) => tree + | (Node {color, left, right}, zipper) => delete color left right zipper + end -let rec _search compare tree elem = +let rec _search compare tree elem = match tree with | Leaf => False - | Node {left, value, right} => - match compare elem value with - | Less => _search compare left elem - | Greater => _search compare right elem - | Equal => True - end + | Node {left, value, right} => + match compare elem value with + | Lt => _search compare left elem + | Gt => _search compare right elem + | Eq => True + end end -let rec setFoldl tree func acc = +let rec setFoldl tree func acc = match tree with - | Leaf => acc - | Node {left, value, right} => - setFoldl right func (func value (setFoldl left func acc)) + | Leaf => acc + | Node {left, value, right} => + setFoldl right func (func value (setFoldl left func acc)) end let rec setFoldr tree func acc = - match tree with - | Leaf => acc - | Node {left, value, right} => - setFoldr left func (func value (setFoldr right func acc)) + match tree with + | Leaf => acc + | Node {left, value, right} => + setFoldr left func (func value (setFoldr right func acc)) end -let rec toList tree acc = - match tree with - | Leaf => acc - | Node {left, value, right} => - toList left (value :: toList right acc) +let rec toList acc tree = + match tree with + | Leaf => acc + | Node {left, value, right} => + toList (value :: toList acc right) left end let rec union compare tree1 tree2 = match tree1 with - | Leaf => tree2 - | Node {left = left1, value = key1, right = right1} => - match tree2 with - | Leaf => tree1 - | Node => - let (_,left2,right2) = split (fn key2 => compare key1 key2) tree2 in - joinVal (union compare left1 left2) key1 - (union compare right1 right2) - end + | Leaf => tree2 + | Node {left = left1, value = key1, right = right1} => + match tree2 with + | Leaf => tree1 + | Node => + let (_,left2,right2) = split (compare key1) tree2 in + let left' = union compare left1 left2 + let right' = union compare right1 right2 in + joinVal left' key1 right' + end end let rec intersection compare tree1 tree2 = match tree1 with + | Leaf => Leaf + | Node {left = left1, value = key1, right = right1} => + match tree2 with | Leaf => Leaf - | Node {left = left1, value = key1, right = right1} => - match tree2 with - | Leaf => Leaf - | _ => let (value_out, left2, right2) = - split (fn key2 => compare key1 key2) tree2 - in let left = intersection compare left1 left2 - in let right = intersection compare right1 right2 - in - match value_out with - | Some _ => joinVal left key1 right - | None => join left right - end + | _ => + let (value_out, left2, right2) = split (compare key1) tree2 + let left = intersection compare left1 left2 + let right = intersection compare right1 right2 + in + match value_out with + | Some _ => joinVal left key1 right + | None => join left right end + end end -let rec difference compare tree1 tree2 = - match tree1 with - | Leaf => Leaf - | Node {left = left1, value = key1, right = right1} => - match tree2 with - | Leaf => tree1 - | _ => - let (value_out, left2, right2) = - split (fn key2 => compare key1 key2) tree2 - in let left = difference compare left1 left2 - in let right = difference compare right1 right2 - in - match value_out with - | Some _ => join left right - | None => joinVal left key1 right - end - end +let rec difference compare tree1 tree2 = + match tree1 with + | Leaf => Leaf + + | Node {left = left1, value = key1, right = right1} => + match tree2 with + | Leaf => tree1 + | _ => + let (value_out, left2, right2) = split (compare key1) tree2 + let left = difference compare left1 left2 + let right = difference compare right1 right2 + in + match value_out with + | Some _ => join left right + | None => joinVal left key1 right + end + end end -let subset compare set1 set2 = subsetMain compare (T set1 Nil) (T set2 Nil) +let eq compare set1 set2 = eqMain compare (T set1 Nil) (T set2 Nil) -let _range compare tree left right = - match (left,right) with - | (Inclusion left, Inclusion right) => - let (_, tree') = partionLt compare tree left in - let (tree'',_) = partionGt compare tree' right in tree'' - | (Exclusion left, Inclusion right) => - let (_, tree') = partionGt compare tree left in - let (tree'',_) = partionGt compare tree' right in tree'' - | (Inclusion left, Exclusion right) => - let (_, tree') = partionLt compare tree left in - let (tree'',_) = partionLt compare tree' right in tree'' - | (Exclusion left, Exclusion right) => - let (_, tree') = partionGt compare tree left in - let (tree'',_) = partionLt compare tree' right in tree'' - end +let subset compare set1 set2 = subsetMain compare (T set1 Nil) (T set2 Nil) -let range compare tree incl left incr right = - match (incl,incr) with - | (False,False) => _range compare tree (Exclusion left) (Exclusion right) - | (False,True) => _range compare tree (Exclusion left) (Inclusion right) - | (True,False) => _range compare tree (Inclusion left) (Exclusion right) - | (True,True) => _range compare tree (Inclusion left) (Inclusion right) - end - -let rec leastGt compare tree val = +let rec leastGt compare tree val = match tree with | Leaf => None - | Node {left, value = key, right} => - match compare val key with - | Less => let x = leastGt compare left val in - match x with - | None => Some key - | _ => x - end - | Equal => least right - | Greater => leastGt compare right val + | Node {left, value = key, right} => + match compare val key with + | Lt => + let x = leastGt compare left val in + match x with + | None => Some key + | _ => x end - end + | Eq => least right + | Gt => leastGt compare right val + end + end let leastGtErr compare tree val = match leastGt compare tree val with @@ -420,18 +413,18 @@ let leastGtErr compare tree val = end let rec leastGeq compare tree val = - match tree with + match tree with | Leaf => None - | Node {left, value = key, right} => - match compare val key with - | Less => - match leastGeq compare left val with - | None => Some key - | x => x - end - | Equal => Some val - | Greater => leastGeq compare right val + | Node {left, value = key, right} => + match compare val key with + | Lt => + match leastGeq compare left val with + | None => Some key + | x => x end + | Eq => Some val + | Gt => leastGeq compare right val + end end let leastGeqErr compare tree val = @@ -441,18 +434,18 @@ let leastGeqErr compare tree val = end let rec greatestLt compare tree val = - match tree with - | Leaf => None - | Node {left, value = key, right} => - match compare val key with - | Less => greatestLt compare left val - | Equal => greatest left - | Greater => - match greatestLt compare right val with - | None => Some key - | x => x - end - end + match tree with + | Leaf => None + | Node {left, value = key, right} => + match compare val key with + | Lt => greatestLt compare left val + | Eq => greatest left + | Gt => + match greatestLt compare right val with + | None => Some key + | x => x + end + end end let greatestLtErr compare tree val = @@ -461,19 +454,19 @@ let greatestLtErr compare tree val = | Some x => x end -let rec greatestLeq compare tree val = +let rec greatestLeq compare tree val = match tree with - | Leaf => None - | Node {left, value = key, right} => - match compare val key with - | Less => greatestLeq compare left val - | Equal => Some val - | Greater => - match greatestLeq compare right val with - | None => Some key - | x => x - end - end + | Leaf => None + | Node {left, value = key, right} => + match compare val key with + | Lt => greatestLeq compare left val + | Eq => Some val + | Gt => + match greatestLeq compare right val with + | None => Some key + | x => x + end + end end let greatestLeqErr compare tree val = @@ -483,7 +476,7 @@ let greatestLeqErr compare tree val = end -pub let make {Val} (compare : Val -> Val -> [] Ordered) = Set { +pub let make {Val} (compare : Val -> Val ->[] Ordered) = Set { T = Tree Val , empty = empty , method isEmpty = isEmpty @@ -492,16 +485,14 @@ pub let make {Val} (compare : Val -> Val -> [] Ordered) = Set { , method member = member compare , method foldl = setFoldl , method foldr = setFoldr - , method toList = fn tree => toList tree [] + , method toList = toList [] , method union = union compare , method intersection = intersection compare , method difference = difference compare - , method eq = fn set1 set2 => - eqMain (fn e1 e2 => (compare e1 e2).toComparable) (T set1 Nil) (T set2 Nil) + , method eq = eq compare , method subset = subset compare , method partionLt = partionLt compare , method partionGt = partionGt compare - , method range = range compare , method lowerBound = least , method lowerBoundErr = leastErr , method upperBound = greatest diff --git a/test/stdlib/stdlib0002_Map.fram b/test/stdlib/stdlib0002_Map.fram index 0b798a4c..18698bc9 100755 --- a/test/stdlib/stdlib0002_Map.fram +++ b/test/stdlib/stdlib0002_Map.fram @@ -1,88 +1,87 @@ import Map import open List -import open Prelude -let lt (v1 : Int) (v2 : Int) = - if v1 < v2 then Less - else if v2 < v1 then Greater - else Equal +let lt (v1 : Int) (v2 : Int) = + if v1 < v2 then Lt + else if v2 < v1 then Gt + else Eq let Map.Map {module IntMap} = Map.make lt let x = IntMap.empty -# insert check +# insert check let y = x.insert 1 1 let z = x.insert 1 "a" -# isEmpty check +# isEmpty check let _ = assert {msg="Failed isEmpty"} (y.isEmpty == False) let _ = assert {msg="Failed isEmpty"} (z.isEmpty == False) let _ = assert {msg="Failed isEmpty"} (y.remove 1 >. isEmpty) -# domain check -let z = y.insert 2 1 >. insert 3 2 >. insert 4 3 -let _ = assert {msg="Failed domain"} - (z.domain == [1,2,3,4] && z.toValueList == [1,1,2,3]) +# domain check +let z = y.insert 2 1 >. insert 3 2 >. insert 4 3 +let _ = assert {msg="Failed domain"} + (z.domain == [1,2,3,4] && z.toValueList == [1,1,2,3]) -# toList check -let _ = assert {msg="Failed toList"} ((z.toList.foldLeft - (fn acc (key,val) => val :: acc) []) == [1,1,2,3].rev) +# toList check +let _ = assert {msg="Failed toList"} ((z.toList.foldLeft + (fn acc (key,val) => val :: acc) []) == [1,1,2,3].rev) -# foldl check -let _ = assert {msg="Failed foldl"} +# foldl check +let _ = assert {msg="Failed foldl"} (z.foldl (fn key val acc => key :: acc) [] == [1,2,3,4].rev) - -# member check + +# member check let _ = assert {msg="Failed member"} (z.member 1) -# find check -let _ = assert {msg="Failed find"} +# find check +let _ = assert {msg="Failed find"} (match z.find 1 with | None => False | _ => True end) -# operate change check -let _ = assert {msg="Failed operate"} - (snd (z.operate 1 (fn () => Some 2) (fn a => Some 0)) - >. toValueList == [0,1,2,3]) - -# operate add check -let _ = assert {msg="Failed operate"} - (snd (z.operate 0 (fn () => Some 2) (fn a => Some 0)) - >. toValueList == [2,1,1,2,3]) - -# map check +# update change check +let _ = assert {msg="Failed update"} + (let f a = + match a with + | None => Some 2 + | Some _ => Some 0 + end in + z.update 1 f + >. toValueList == [0,1,2,3]) + +# update add check +let _ = assert {msg="Failed update"} + (let f a = + match a with + | None => Some 2 + | Some _ => Some 0 + end in + z.update 0 f + >. toValueList == [2,1,1,2,3]) + +# map check let _ = assert {msg="Failed map"} - (z.mapVal (fn x => if x == x.shiftr 1 >. shiftl 1 then -x else x) - >. toValueList == [1,1,(0-2),3]) + (z.mapVal (fn x => if x == x.shiftr 1 >. shiftl 1 then -x else x) + >. toValueList == [1,1,(0-2),3]) -# union check +# union check let y = x.insert 1.neg 2 >. insert 2.neg 3 >. insert 0 1 >. insert 1 10 -let w = z.union y (fn key val1 val2 => val2) -let _ = assert {msg="Failed union"} (w.toValueList == [3,2,1,10,1,2,3]) +let w = z.union y (fn key val1 val2 => val2) +let _ = assert {msg="Failed union"} (w.toValueList == [3,2,1,10,1,2,3]) -# partion check +# partion check let q = w.partion 0 -let _ = assert {msg="Failed partion"} (fst (fst q) >. toValueList == [3,2]) -let _ = assert {msg="Failed partion"} (snd q >. toValueList == [10,1,2,3]) +let _ = assert {msg="Failed partion"} (fst (fst q) >. toValueList == [3,2]) +let _ = assert {msg="Failed partion"} (snd q >. toValueList == [10,1,2,3]) -# partionLt check +# partionLt check let q = w.partionLt 0 -let _ = assert {msg="Failed partionLt"} (fst q >. toValueList == [3,2,1]) -let _ = assert {msg="Failed partionLt"} (snd q >. toValueList == [10,1,2,3]) +let _ = assert {msg="Failed partionLt"} (fst q >. toValueList == [3,2,1]) +let _ = assert {msg="Failed partionLt"} (snd q >. toValueList == [10,1,2,3]) -# partionGt check +# partionGt check let q = w.partionGt 0 -let _ = assert {msg="Failed partionGt"} (fst q >. toValueList == [3,2]) -let _ = assert {msg="Failed partionGt"} (snd q >. toValueList == [1,10,1,2,3]) - -# range check -let q = w.range False 0 False 2 -let _ = assert {msg="Failed range"} (q.toValueList == [10]) -let q = w.range True 0 True 2 -let _ = assert {msg="Failed range"} (q.toValueList == [1,10,1]) -let _ = assert {msg="Failed range"} - (w.range True 0 False 2 >. toValueList == [1,10]) -let _ = assert {msg="Failed range"} - (w.range False 0 True 2 >. toValueList == [10,1]) +let _ = assert {msg="Failed partionGt"} (fst q >. toValueList == [3,2]) +let _ = assert {msg="Failed partionGt"} (snd q >. toValueList == [1,10,1,2,3]) diff --git a/test/stdlib/stdlib0003_Set.fram b/test/stdlib/stdlib0003_Set.fram index 35ac391c..9f58d451 100755 --- a/test/stdlib/stdlib0003_Set.fram +++ b/test/stdlib/stdlib0003_Set.fram @@ -1,76 +1,71 @@ import Set import open List -import open Prelude -let lt (v1 : Int) (v2 : Int) = - if v1 < v2 then Less - else if v2 < v1 then Greater - else Equal +let lt (v1 : Int) (v2 : Int) = + if v1 < v2 then Lt + else if v2 < v1 then Gt + else Eq let Set.Set {module IntSet} = Set.make lt -# empty check +# empty check let x = IntSet.empty -let _ = assert {msg="Failed empty"} (x.isEmpty) +let _ = assert {msg="Failed empty"} (x.isEmpty) let x = x.insert 0 -# toList check -let _ = assert {msg="Failed toList"} (x.toList == [0]) +# toList check +let _ = assert {msg="Failed toList"} (x.toList == [0]) -# insert check +# insert check let y = x.insert 1 -let _ = assert {msg="Failed insert"} (y.toList == [0,1]) -let _ = assert {msg="Failed insert"} (y.insert 2 >. toList == [0,1,2]) +let _ = assert {msg="Failed insert"} (y.toList == [0,1]) +let _ = assert {msg="Failed insert"} (y.insert 2 >. toList == [0,1,2]) -# remove check -let y = y.insert 2 >. insert 3 -let _ = assert {msg="Failed remove"} (y.remove 1 >. toList == [0,2,3]) +# remove check +let y = y.insert 2 >. insert 3 +let _ = assert {msg="Failed remove"} (y.remove 1 >. toList == [0,2,3]) -# member check -let _ = assert {msg="Failed check"} (y.member 1) -let _ = assert {msg="Failed check"} (not (y.member 10)) +# member check +let _ = assert {msg="Failed check"} (y.member 1) +let _ = assert {msg="Failed check"} (not (y.member 10)) -# foldl/r check -let _ = assert {msg="Failed foldl"} (y.foldl (fn x acc => x + acc) 0 == 6) -let _ = assert {msg="Failed foldr"} (y.foldr (fn x acc => x + acc) 0 == 6) +# foldl/r check +let _ = assert {msg="Failed foldl"} (y.foldl (fn x acc => x + acc) 0 == 6) +let _ = assert {msg="Failed foldr"} (y.foldr (fn x acc => x + acc) 0 == 6) -# union check +# union check let x = x.insert 4 >. insert 5 >. insert 6 -let _ = assert {msg="Failed union"} (y.union x >. toList == [0,1,2,3,4,5,6]) +let _ = assert {msg="Failed union"} (y.union x >. toList == [0,1,2,3,4,5,6]) -# intersection check -let _ = assert {msg="Failed intersection"} (x.intersection y >. toList == [0]) +# intersection check +let _ = assert {msg="Failed intersection"} (x.intersection y >. toList == [0]) -# diffrence check -let _ = assert {msg="Failed difference"} (y.difference x >. toList == [1,2,3]) -let _ = assert {msg="Failed difference"} (x.difference y >. toList == [4,5,6]) +# diffrence check +let _ = assert {msg="Failed difference"} (y.difference x >. toList == [1,2,3]) +let _ = assert {msg="Failed difference"} (x.difference y >. toList == [4,5,6]) -# eq check -let _ = assert {msg="Failed eq"} (x.eq x) -let _ = assert {msg="Failed eq"} (not (x.eq y)) +# eq check +let _ = assert {msg="Failed eq"} (x.eq x) +let _ = assert {msg="Failed eq"} (not (x.eq y)) -# subset check -let _ = assert {msg="Failed subset"} (IntSet.empty.subset x) -let _ = assert {msg="Failed subset"} - (IntSet.empty.insert 0 >. insert 1 >. subset y) -let _ = assert {msg="Failed subset"} (not (x.subset y)) +# subset check +let _ = assert {msg="Failed subset"} (IntSet.empty.subset x) +let _ = assert {msg="Failed subset"} + (IntSet.empty.insert 0 >. insert 1 >. subset y) +let _ = assert {msg="Failed subset"} (not (x.subset y)) -# partionLt check -let _ = assert {msg="Failed partionLt"} - (fst (y.partionLt 2) >. toList == [0,1]) -let _ = assert {msg="Failed partionLt"} - (snd (y.partionLt 2) >. toList == [2,3]) +# partionLt check +let _ = assert {msg="Failed partionLt"} + (fst (y.partionLt 2) >. toList == [0,1]) +let _ = assert {msg="Failed partionLt"} + (snd (y.partionLt 2) >. toList == [2,3]) -# range check -let _ = assert {msg="Failed range"} - (y.range True 1 True 2 >. toList == [1,2]) - -# lowerBound check +# lowerBound check let _ = assert {msg="Failed lowerBound"} - (match y.lowerBound with | Some x => x == 0 | _ => False end) + (match y.lowerBound with | Some x => x == 0 | _ => False end) -# upperBound check -let _ = assert {msg="Failed upperBound"} +# upperBound check +let _ = assert {msg="Failed upperBound"} (match y.upperBound with | Some x => x == 3 | _ => False end) - + From c4675a974d36d5616b332425abc8a6a24eddcc8a Mon Sep 17 00:00:00 2001 From: Szymon Jedras Date: Thu, 13 Mar 2025 00:16:13 +0100 Subject: [PATCH 22/27] Replacing '\t' with ' ' --- lib/Queue.fram | 14 +-- lib/RedBlackTree.fram | 198 ++++++++++++++++---------------- test/stdlib/stdlib0002_Map.fram | 20 ++-- 3 files changed, 116 insertions(+), 116 deletions(-) diff --git a/lib/Queue.fram b/lib/Queue.fram index bc9ec0b5..d8093f2d 100755 --- a/lib/Queue.fram +++ b/lib/Queue.fram @@ -8,8 +8,8 @@ data NotNegativeInt = Zero | Positive of Int let addOne value = match value with - | Zero => Positive 1 - | Positive n => Positive (n+1) + | Zero => Positive 1 + | Positive n => Positive (n+1) end let subOne value = @@ -76,7 +76,7 @@ let check queue = if leq lenr lenf then exec_twice queue else ( let newstate = Reversing Zero f [] r [] in - exec_twice (HMQueue (add lenf lenr) f newstate Zero []) + exec_twice (HMQueue (add lenf lenr) f newstate Zero []) ) end @@ -90,7 +90,7 @@ pub let isEmpty queue = let snoc queue value = match queue with | HMQueue lenf f state lenr r => - check (HMQueue lenf f state (addOne lenr) (value :: r)) + check (HMQueue lenf f state (addOne lenr) (value :: r)) end let head queue = @@ -105,7 +105,7 @@ let tail queue = | HMQueue Zero _ _ _ _ => emptyQueue | HMQueue _ [] _ _ _ => emptyQueue | HMQueue lenf (x::xs) state lenr r => - check (HMQueue (subOne lenf) xs (invalidate state) lenr r) + check (HMQueue (subOne lenf) xs (invalidate state) lenr r) end let foldlRotationState f acc state = @@ -131,8 +131,8 @@ pub let foldlQueue queue f acc = | HMQueue _ list1 state _ list2 => List.foldLeft f (foldlRotationState f - (List.foldLeft f acc list1) - state) + (List.foldLeft f acc list1) + state) list2 end diff --git a/lib/RedBlackTree.fram b/lib/RedBlackTree.fram index 3f81f758..cceb1fb0 100755 --- a/lib/RedBlackTree.fram +++ b/lib/RedBlackTree.fram @@ -26,8 +26,8 @@ pub let empty = Leaf pub let size tree = match tree with - | Leaf => 0 - | Node {size} => size + | Leaf => 0 + | Node {size} => size end pub let makeNode color left value right = @@ -41,10 +41,10 @@ pub let rec zip tree zipper = | [] => tree | Left color value right :: rest => - zip (makeNode color tree value right) rest + zip (makeNode color tree value right) rest | Right color left value :: rest => - zip (makeNode color left value tree) rest + zip (makeNode color left value tree) rest end @@ -53,67 +53,67 @@ pub let rec zipRed value left right zipper = | [] => makeNode Black left value right | Left Black value1 right1 :: rest => - zip (makeNode Black (makeNode Red left value right) value1 right1) rest + zip (makeNode Black (makeNode Red left value right) value1 right1) rest | Right Black left1 value1 :: rest => - zip (makeNode Black left1 value1 (makeNode Red left value right)) rest + zip (makeNode Black left1 value1 (makeNode Red left value right)) rest | Left Red value1 right1 :: - Left _ value2 - (Node {color = Red, size = size3, left = left3, - value = value3, right = right3}) :: rest => - let left' = makeNode Red left value right - let right' = construct Black size3 left3 value3 right3 in - zipRed value2 (makeNode Black left' value1 right1) right' rest + Left _ value2 + (Node {color = Red, size = size3, left = left3, + value = value3, right = right3}) :: rest => + let left' = makeNode Red left value right + let right' = construct Black size3 left3 value3 right3 in + zipRed value2 (makeNode Black left' value1 right1) right' rest | Left Red value1 right1 :: - Right _ - (Node {color = Red, size = size3, left = left3, - value = value3, right = right3}) value2 :: rest => - let left' = construct Black size3 left3 value3 right3 - let right' = makeNode Red left value right in - zipRed value2 left' (makeNode Black right' value1 right1) rest + Right _ + (Node {color = Red, size = size3, left = left3, + value = value3, right = right3}) value2 :: rest => + let left' = construct Black size3 left3 value3 right3 + let right' = makeNode Red left value right in + zipRed value2 left' (makeNode Black right' value1 right1) rest | Right Red left1 value1 :: - Left _ value2 - (Node {color = Red, size = size3, left = left3, - value = value3, right = right3}) :: rest => - let left' = makeNode Red left value right - let right' = construct Black size3 left3 value3 right3 in - zipRed value2 (makeNode Black left1 value1 left') right' rest + Left _ value2 + (Node {color = Red, size = size3, left = left3, + value = value3, right = right3}) :: rest => + let left' = makeNode Red left value right + let right' = construct Black size3 left3 value3 right3 in + zipRed value2 (makeNode Black left1 value1 left') right' rest | Right Red left1 value1 :: - Right _ (Node {color = Red, size = size3, left = left3, - value = value3, right = right3}) value2 :: rest => - let left' = construct Black size3 left3 value3 right3 - let right' = makeNode Red left value right in - zipRed value2 left' (makeNode Black left1 value1 right') rest + Right _ (Node {color = Red, size = size3, left = left3, + value = value3, right = right3}) value2 :: rest => + let left' = construct Black size3 left3 value3 right3 + let right' = makeNode Red left value right in + zipRed value2 left' (makeNode Black left1 value1 right') rest | Left Red value1 right1 :: Left _ value2 node3 :: rest => - let left' = makeNode Red left value right - let right' = makeNode Red right1 value2 node3 in - zip (makeNode Black left' value1 right') rest + let left' = makeNode Red left value right + let right' = makeNode Red right1 value2 node3 in + zip (makeNode Black left' value1 right') rest | Left Red value1 right1 :: Right _ node3 value2 :: rest => - let left' = makeNode Red node3 value2 left - let right' = makeNode Red right value1 right1 in - zip (makeNode Black left' value right') rest + let left' = makeNode Red node3 value2 left + let right' = makeNode Red right value1 right1 in + zip (makeNode Black left' value right') rest | Right Red left1 value1 :: Left _ value2 node3 :: rest => - let left' = makeNode Red left1 value1 left - let right' = makeNode Red right value2 node3 in - zip (makeNode Black left' value right') rest + let left' = makeNode Red left1 value1 left + let right' = makeNode Red right value2 node3 in + zip (makeNode Black left' value right') rest | Right Red left1 value1 :: Right _ node3 value2 :: rest => - let left' = makeNode Red node3 value2 left1 - let right' = makeNode Red left value right in - zip (makeNode Black left' value1 right') rest + let left' = makeNode Red node3 value2 left1 + let right' = makeNode Red left value right in + zip (makeNode Black left' value1 right') rest | Left Red value1 right1 :: [] => - makeNode Black (makeNode Red left value right) value1 right1 + makeNode Black (makeNode Red left value right) value1 right1 | Right Red left1 value1 :: [] => - makeNode Black left1 value1 (makeNode Red left value right) + makeNode Black left1 value1 (makeNode Red left value right) end @@ -122,63 +122,63 @@ pub let rec zipBlack tree zipper = | [] => tree | Left color1 value1 - (Node {left = left2, value = value2, - right = (Node {color = Red, size = size3, - left = left3, value = value3, right = right3})}) :: - rest => - let left' = makeNode Black tree value1 left2 - let right' = construct Black size3 left3 value3 right3 in - zip (makeNode color1 left' value2 right') rest + (Node {left = left2, value = value2, + right = (Node {color = Red, size = size3, + left = left3, value = value3, right = right3})}) :: + rest => + let left' = makeNode Black tree value1 left2 + let right' = construct Black size3 left3 value3 right3 in + zip (makeNode color1 left' value2 right') rest | Right color1 (Node { left = (Node {color = Red, size = size3, left = left3, - value = value3, right = right3}), value = value2, right = right2}) - value1 :: rest => - let left' = construct Black size3 left3 value3 right3 - let right' = makeNode Black right2 value1 tree in - zip (makeNode color1 left' value2 right') rest + value = value3, right = right3}), value = value2, right = right2}) + value1 :: rest => + let left' = construct Black size3 left3 value3 right3 + let right' = makeNode Black right2 value1 tree in + zip (makeNode color1 left' value2 right') rest | Left color1 value1 (Node {left = (Node {color = Red, left = left3, - value = value3, right = right3}), - value = value2, right = right2}) :: rest => - let left' = makeNode Black tree value1 left3 - let right' = makeNode Black right3 value2 right2 in - zip (makeNode color1 left' value3 right') rest + value = value3, right = right3}), + value = value2, right = right2}) :: rest => + let left' = makeNode Black tree value1 left3 + let right' = makeNode Black right3 value2 right2 in + zip (makeNode color1 left' value3 right') rest | Right color1 (Node {left = left2, value = value2, right = - (Node {color = Red, left = left3, value = value3, right = right3})}) - value1 :: rest => - let left' = makeNode Black left2 value2 left3 - let right' = makeNode Black right3 value1 tree in - zip (makeNode color1 left' value3 right') rest + (Node {color = Red, left = left3, value = value3, right = right3})}) + value1 :: rest => + let left' = makeNode Black left2 value2 left3 + let right' = makeNode Black right3 value1 tree in + zip (makeNode color1 left' value3 right') rest | Left Red value1 (Node {size = size2, left = left2, - value = value2, right = right2}) :: rest => - let right' = construct Red size2 left2 value2 right2 in - zip (makeNode Black tree value1 right') rest + value = value2, right = right2}) :: rest => + let right' = construct Red size2 left2 value2 right2 in + zip (makeNode Black tree value1 right') rest | Right Red (Node {size = size2, left = left2, - value = value2, right = right2}) value1 :: rest => - let left' = construct Red size2 left2 value2 right2 in - zip (makeNode Black left' value1 tree) rest + value = value2, right = right2}) value1 :: rest => + let left' = construct Red size2 left2 value2 right2 in + zip (makeNode Black left' value1 tree) rest | Left Black value1 (Node {color = Black, size = size2, left = left2, - value = value2, right = right2}) :: rest => - let right' = construct Red size2 left2 value2 right2 in - zipBlack (makeNode Black tree value1 right') rest + value = value2, right = right2}) :: rest => + let right' = construct Red size2 left2 value2 right2 in + zipBlack (makeNode Black tree value1 right') rest | Right Black (Node {color = Black, size = size2, left = left2, - value = value2, right = right2}) value1 :: rest => - let left' = construct Red size2 left2 value2 right2 in - zipBlack (makeNode Black left' value1 tree) rest + value = value2, right = right2}) value1 :: rest => + let left' = construct Red size2 left2 value2 right2 in + zipBlack (makeNode Black left' value1 tree) rest | Left Black value1 (Node {color = Red, left = left2, - value = value2, right = right2}) :: rest => - zipBlack tree (Left Red value1 left2 :: Left Black value2 right2 :: rest) + value = value2, right = right2}) :: rest => + zipBlack tree (Left Red value1 left2 :: Left Black value2 right2 :: rest) | Right Black (Node {color = Red, left = left2, value = value2, - right = right2}) value1 :: rest => - let rest' = Right Red right2 value1 :: Right Black left2 value2 :: rest in - zipBlack tree rest' + right = right2}) value1 :: rest => + let rest' = Right Red right2 value1 :: Right Black left2 value2 :: rest in + zipBlack tree rest' # Impossible | Left _ _ Leaf :: _ => impossible () @@ -204,23 +204,23 @@ pub let rec searchMin tree zipper = match tree with | Leaf => zipper | Node {color, left, value, right} => - searchMin left (Left color value right :: zipper) + searchMin left (Left color value right :: zipper) end pub let rec searchMax tree zipper = match tree with | Leaf => zipper | Node {color, left, value, right} => - searchMax right (Right color left value:: zipper) + searchMax right (Right color left value:: zipper) end pub let deleteNearLeaf color child zipper = match color with | Red => zip Leaf zipper | Black => - match child with + match child with | Node {value} => - zip (makeNode Black Leaf value Leaf) zipper + zip (makeNode Black Leaf value Leaf) zipper | Leaf => zipBlack Leaf zipper end end @@ -230,23 +230,23 @@ pub let delete color left right zipper = | Leaf => match left with | Leaf => - match color with + match color with | Red => zip Leaf zipper | Black => zipBlack Leaf zipper end | _ => match searchMax left [] with | Right colorLeftMin leftLeftMin valueLeftMin :: zipperr => - deleteNearLeaf colorLeftMin leftLeftMin - (List.append zipperr (Left color valueLeftMin right :: zipper)) + deleteNearLeaf colorLeftMin leftLeftMin + (List.append zipperr (Left color valueLeftMin right :: zipper)) | _ => Leaf end end | _ => match searchMin right [] with | Left colorRightMin valueRightMin rightRightMin :: zipperr => - deleteNearLeaf colorRightMin rightRightMin - (List.append zipperr (Right color left valueRightMin :: zipper)) + deleteNearLeaf colorRightMin rightRightMin + (List.append zipperr (Right color left valueRightMin :: zipper)) | _ => Leaf end end @@ -254,7 +254,7 @@ pub let delete color left right zipper = pub let blacken tree = match tree with | Node {color = Red, size, left, value, right} => - construct Black size left value right + construct Black size left value right | _ => tree end @@ -270,18 +270,18 @@ pub let rec searchHeight leftward target tree zipper = | Leaf => (Leaf, zipper) | Node {color=Red,left,value,right} => if leftward then - searchHeight leftward target left (Left Red value right :: zipper) + searchHeight leftward target left (Left Red value right :: zipper) else - searchHeight leftward target right (Right Red left value :: zipper) + searchHeight leftward target right (Right Red left value :: zipper) | Node {color=Black,left,value,right} => if 0 == target then - (tree,zipper) + (tree,zipper) else if leftward then - searchHeight leftward (target - 1) left - (Left Black value right :: zipper) + searchHeight leftward (target - 1) left + (Left Black value right :: zipper) else - searchHeight leftward (target - 1) right - (Right Black left value :: zipper) + searchHeight leftward (target - 1) right + (Right Black left value :: zipper) end pub let joinVal left value right = diff --git a/test/stdlib/stdlib0002_Map.fram b/test/stdlib/stdlib0002_Map.fram index 18698bc9..a3a9437b 100755 --- a/test/stdlib/stdlib0002_Map.fram +++ b/test/stdlib/stdlib0002_Map.fram @@ -42,21 +42,21 @@ let _ = assert {msg="Failed find"} # update change check let _ = assert {msg="Failed update"} - (let f a = - match a with - | None => Some 2 - | Some _ => Some 0 - end in + (let f a = + match a with + | None => Some 2 + | Some _ => Some 0 + end in z.update 1 f >. toValueList == [0,1,2,3]) # update add check let _ = assert {msg="Failed update"} - (let f a = - match a with - | None => Some 2 - | Some _ => Some 0 - end in + (let f a = + match a with + | None => Some 2 + | Some _ => Some 0 + end in z.update 0 f >. toValueList == [2,1,1,2,3]) From 8f31eb6aa5f27fefb8798c9bef2f00fb12c8c581 Mon Sep 17 00:00:00 2001 From: Patrycja Balik Date: Tue, 25 Mar 2025 13:41:47 +0100 Subject: [PATCH 23/27] Fix file permissions --- .github/workflows/Test.yml | 0 .gitignore | 0 LICENSE | 0 README.md | 0 dune | 0 dune-project | 0 examples/LWT_lexical.fram | 0 examples/Modules/A.fram | 0 examples/Modules/B/A.fram | 0 examples/Modules/B/C/D.fram | 0 examples/Modules/C.fram | 0 examples/Modules/Main.fram | 0 examples/Prolog.fram | 0 examples/Pythagorean.fram | 0 examples/Tick.fram | 0 lib/Base/Assert.fram | 0 lib/Base/Bool.fram | 0 lib/Base/Char.fram | 0 lib/Base/Int.fram | 0 lib/Base/Int64.fram | 0 lib/Base/Operators.fram | 0 lib/Base/Option.fram | 0 lib/Base/String.fram | 0 lib/Base/Types.fram | 0 lib/List.fram | 0 lib/Map.fram | 0 lib/Prelude.fram | 0 lib/Queue.fram | 0 lib/RedBlackTree.fram | 0 lib/Set.fram | 0 src/DblConfig.ml | 0 src/DblParser/Desugar.ml | 0 src/DblParser/Error.ml | 0 src/DblParser/Error.mli | 0 src/DblParser/File.ml | 0 src/DblParser/File.mli | 0 src/DblParser/Import.ml | 0 src/DblParser/Import.mli | 0 src/DblParser/Lexer.mli | 0 src/DblParser/Lexer.mll | 0 src/DblParser/Main.ml | 0 src/DblParser/Main.mli | 0 src/DblParser/Raw.ml | 0 src/DblParser/YaccParser.mly | 0 src/DblParser/dune | 0 src/Eval/Env.ml | 0 src/Eval/Env.mli | 0 src/Eval/Eval.ml | 0 src/Eval/Eval.mli | 0 src/Eval/External.ml | 0 src/Eval/Value.ml | 0 src/Eval/dune | 0 src/InterpLib/Error.ml | 0 src/InterpLib/Error.mli | 0 src/InterpLib/InternalError.ml | 0 src/InterpLib/InternalError.mli | 0 src/InterpLib/TextRangePrinting.ml | 0 src/InterpLib/TextRangePrinting.mli | 0 src/InterpLib/dune | 0 src/Lang/Core.ml | 0 src/Lang/Core.mli | 0 src/Lang/CorePriv/BuiltinType.ml | 0 src/Lang/CorePriv/Effect.ml | 0 src/Lang/CorePriv/Kind.ml | 0 src/Lang/CorePriv/SExprPrinter.ml | 0 src/Lang/CorePriv/Subst.ml | 0 src/Lang/CorePriv/Subst.mli | 0 src/Lang/CorePriv/Syntax.ml | 0 src/Lang/CorePriv/Type.ml | 0 src/Lang/CorePriv/TypeBase.ml | 0 src/Lang/CorePriv/WellTypedInvariant.ml | 0 src/Lang/CorePriv/dune | 0 src/Lang/Surface.ml | 0 src/Lang/Unif.ml | 0 src/Lang/Unif.mli | 0 src/Lang/UnifPriv/BuiltinType.ml | 0 src/Lang/UnifPriv/Effect.ml | 0 src/Lang/UnifPriv/KindBase.ml | 0 src/Lang/UnifPriv/KindBase.mli | 0 src/Lang/UnifPriv/Name.ml | 0 src/Lang/UnifPriv/Scope.ml | 0 src/Lang/UnifPriv/Scope.mli | 0 src/Lang/UnifPriv/Subst.ml | 0 src/Lang/UnifPriv/Subst.mli | 0 src/Lang/UnifPriv/TVar.ml | 0 src/Lang/UnifPriv/TVar.mli | 0 src/Lang/UnifPriv/Type.ml | 0 src/Lang/UnifPriv/TypeBase.ml | 0 src/Lang/UnifPriv/TypeBase.mli | 0 src/Lang/UnifPriv/TypeWhnf.ml | 0 src/Lang/UnifPriv/dune | 0 src/Lang/Untyped.ml | 0 src/Lang/dune | 0 src/Pipeline.ml | 0 src/Pipeline.mli | 0 src/ToCore/Common.ml | 0 src/ToCore/DataType.ml | 0 src/ToCore/DataType.mli | 0 src/ToCore/Env.ml | 0 src/ToCore/Env.mli | 0 src/ToCore/Error.ml | 0 src/ToCore/Error.mli | 0 src/ToCore/Main.ml | 0 src/ToCore/Main.mli | 0 src/ToCore/PatternContext.ml | 0 src/ToCore/PatternMatch.ml | 0 src/ToCore/PatternMatch.mli | 0 src/ToCore/Type.ml | 0 src/ToCore/dune | 0 src/TypeErase.ml | 0 src/TypeInference/Common.ml | 0 src/TypeInference/DataType.ml | 0 src/TypeInference/DataType.mli | 0 src/TypeInference/Def.ml | 0 src/TypeInference/Def.mli | 0 src/TypeInference/Env.ml | 0 src/TypeInference/Env.mli | 0 src/TypeInference/Error.ml | 0 src/TypeInference/Error.mli | 0 src/TypeInference/Expr.ml | 0 src/TypeInference/Expr.mli | 0 src/TypeInference/ExprUtils.ml | 0 src/TypeInference/ExprUtils.mli | 0 src/TypeInference/ImplicitEnv.ml | 0 src/TypeInference/ImplicitEnv.mli | 0 src/TypeInference/Main.ml | 0 src/TypeInference/Main.mli | 0 src/TypeInference/MatchClause.ml | 0 src/TypeInference/MatchClause.mli | 0 src/TypeInference/ModStack.ml | 0 src/TypeInference/ModStack.mli | 0 src/TypeInference/Module.ml | 0 src/TypeInference/Module.mli | 0 src/TypeInference/Name.ml | 0 src/TypeInference/Name.mli | 0 src/TypeInference/Pattern.ml | 0 src/TypeInference/Pattern.mli | 0 src/TypeInference/PolyExpr.ml | 0 src/TypeInference/PolyExpr.mli | 0 src/TypeInference/PreludeTypes.ml | 0 src/TypeInference/PreludeTypes.mli | 0 src/TypeInference/Pretty.ml | 0 src/TypeInference/Pretty.mli | 0 src/TypeInference/RecDefs.ml | 0 src/TypeInference/RecDefs.mli | 0 src/TypeInference/Type.ml | 0 src/TypeInference/Type.mli | 0 src/TypeInference/TypeCheckFix.ml | 0 src/TypeInference/TypeHints.ml | 0 src/TypeInference/TypeHints.mli | 0 src/TypeInference/TypeUtils.ml | 0 src/TypeInference/TypeUtils.mli | 0 src/TypeInference/Unification.ml | 0 src/TypeInference/Unification.mli | 0 src/TypeInference/Uniqueness.ml | 0 src/TypeInference/Uniqueness.mli | 0 src/TypeInference/dune | 0 src/Utils/BRef.ml | 0 src/Utils/BRef.mli | 0 src/Utils/Eq.ml | 0 src/Utils/Map1.ml | 0 src/Utils/Perm.ml | 0 src/Utils/Position.ml | 0 src/Utils/SExpr.ml | 0 src/Utils/SExpr.mli | 0 src/Utils/SyntaxNode.ml | 0 src/Utils/UID.ml | 0 src/Utils/UID.mli | 0 src/Utils/Var.ml | 0 src/Utils/Var.mli | 0 src/Utils/dune | 0 src/dbl.ml | 0 src/dune | 0 test/err/lexer_0000_illegalOp0.fram | 0 test/err/lexer_0001_illegalOp1.fram | 0 test/err/lexer_0002_eofInComment.fram | 0 test/err/parser_0000_illegalBinopPattern.fram | 0 test/err/parser_0001_illegalBinopCtor.fram | 0 test/err/parser_0002_illegalBinopMethod.fram | 0 test/err/tc_0000_implicitLoop.fram | 0 test/err/tc_0001_escapingType.fram | 0 test/err/tc_0002_escapingType.fram | 0 test/err/tc_0004_methodFn.fram | 0 test/err/tc_0005_specialBinops.fram | 0 test/err/tc_0006_unapplicableKind.fram | 0 test/err/tc_0007_missingOptionTypeDef.fram | 0 test/err/tc_0008_invalidOptionTypeConstructors.fram | 0 test/err/tc_0009_polymorphicOptionalArg.fram | 0 test/err/tc_0010_impureNonPositiveRecord.fram | 0 test/err/tc_0011_nonPositiveUVar.fram | 0 test/err/tc_0012_impureExprInPureMatch.fram | 0 test/ok/ok0000_emptyFile.fram | 0 test/ok/ok0001_id.fram | 0 test/ok/ok0002_poly.fram | 0 test/ok/ok0003_local.fram | 0 test/ok/ok0004_fnArg.fram | 0 test/ok/ok0005_let.fram | 0 test/ok/ok0006_fnArg.fram | 0 test/ok/ok0007_letArg.fram | 0 test/ok/ok0008_idHandler.fram | 0 test/ok/ok0009_purityRestriction.fram | 0 test/ok/ok0010_implicit.fram | 0 test/ok/ok0011_implicit.fram | 0 test/ok/ok0012_adt.fram | 0 test/ok/ok0013_emptyADT.fram | 0 test/ok/ok0014_arrows.fram | 0 test/ok/ok0015_ctor.fram | 0 test/ok/ok0016_trivialMatch.fram | 0 test/ok/ok0017_wildcard.fram | 0 test/ok/ok0018_namePattern.fram | 0 test/ok/ok0019_simplePattern.fram | 0 test/ok/ok0020_patternMatch.fram | 0 test/ok/ok0021_simpleMatch.fram | 0 test/ok/ok0022_deepMatch.fram | 0 test/ok/ok0023_letPattern.fram | 0 test/ok/ok0024_letFunc.fram | 0 test/ok/ok0025_letFuncImplicit.fram | 0 test/ok/ok0026_funSugar.fram | 0 test/ok/ok0027_explicitApp.fram | 0 test/ok/ok0028_patArg.fram | 0 test/ok/ok0029_handle.fram | 0 test/ok/ok0030_bt.fram | 0 test/ok/ok0031_explicitArg.fram | 0 test/ok/ok0032_dataArg.fram | 0 test/ok/ok0033_higherKinds.fram | 0 test/ok/ok0034_schemes.fram | 0 test/ok/ok0035_schemes.fram | 0 test/ok/ok0036_schemeAnnot.fram | 0 test/ok/ok0037_checkScheme.fram | 0 test/ok/ok0038_explicitArg.fram | 0 test/ok/ok0039_polymorphicImplicit.fram | 0 test/ok/ok0040_polymorphicFields.fram | 0 test/ok/ok0041_existentialTypes.fram | 0 test/ok/ok0042_existentialTypes.fram | 0 test/ok/ok0043_implicitCtorArgs.fram | 0 test/ok/ok0044_implicitCtorArgs.fram | 0 test/ok/ok0045_recursiveData.fram | 0 test/ok/ok0046_mutualDataRec.fram | 0 test/ok/ok0047_namedParam.fram | 0 test/ok/ok0048_explicitTypeInst.fram | 0 test/ok/ok0049_expilicitInstOrder.fram | 0 test/ok/ok0050_typeArgRename.fram | 0 test/ok/ok0051_existentialTypePattern.fram | 0 test/ok/ok0052_emptyMatch.fram | 0 test/ok/ok0053_firstClassHandler.fram | 0 test/ok/ok0054_firstClassHandler.fram | 0 test/ok/ok0055_complexHandlers.fram | 0 test/ok/ok0056_complexHandlers.fram | 0 test/ok/ok0057_dataArgLabels.fram | 0 test/ok/ok0058_unitState.fram | 0 test/ok/ok0059_effectArg.fram | 0 test/ok/ok0060_returnFinally.fram | 0 test/ok/ok0061_returnFinallyMatch.fram | 0 test/ok/ok0062_theLabel.fram | 0 test/ok/ok0064_typeAnnot.fram | 0 test/ok/ok0066_method.fram | 0 test/ok/ok0067_pureMethod.fram | 0 test/ok/ok0068_shadowCtors.fram | 0 test/ok/ok0069_effectCtorArg.fram | 0 test/ok/ok0070_effectMethodArg.fram | 0 test/ok/ok0071_numbers.fram | 0 test/ok/ok0072_strings.fram | 0 test/ok/ok0073_extern.fram | 0 test/ok/ok0074_implicitWithType.fram | 0 test/ok/ok0075_effectsFromImplicits.fram | 0 test/ok/ok0076_ifExpr.fram | 0 test/ok/ok0077_effectResume.fram | 0 test/ok/ok0078_unitMethods.fram | 0 test/ok/ok0079_impureMethod.fram | 0 test/ok/ok0080_moduleDef.fram | 0 test/ok/ok0081_nestedModule.fram | 0 test/ok/ok0082_moduleDataDef.fram | 0 test/ok/ok0083_pubPatternMatch.fram | 0 test/ok/ok0084_operators.fram | 0 test/ok/ok0085_letChecked.fram | 0 test/ok/ok0086_optionState.fram | 0 test/ok/ok0087_opratorOverloading.fram | 0 test/ok/ok0088_abstractData.fram | 0 test/ok/ok0089_pubPat.fram | 0 test/ok/ok0090_lists.fram | 0 test/ok/ok0091_namedParamMethod.fram | 0 test/ok/ok0092_multipleNamedMethodParams.fram | 0 test/ok/ok0093_specialBinops.fram | 0 test/ok/ok0094_unaryIf.fram | 0 test/ok/ok0095_wildcardTypeParam.fram | 0 test/ok/ok0096_fixTypeAnnot.fram | 0 test/ok/ok0097_recursion.fram | 0 test/ok/ok0098_mutualRecursion.fram | 0 test/ok/ok0099_nestedEffArrows.fram | 0 test/ok/ok0100_polymorphicRecursion.fram | 0 test/ok/ok0101_implicitParamsRecord.fram | 0 test/ok/ok0102_simpleRecord.fram | 0 test/ok/ok0103_genericRecords.fram | 0 test/ok/ok0104_chars.fram | 0 test/ok/ok0105_recFunWithNamedParam.fram | 0 test/ok/ok0106_recursiveMethod.fram | 0 test/ok/ok0107_polymorphicRecursion.fram | 0 test/ok/ok0108_modulePattern.fram | 0 test/ok/ok0109_fieldPattern.fram | 0 test/ok/ok0110_publicModulePattern.fram | 0 test/ok/ok0111_optionalParams.fram | 0 test/ok/ok0112_pureRecord.fram | 0 test/ok/ok0113_pureMatchingNonrecUVar.fram | 0 test/ok/ok0114_pureTail.fram | 0 test/ok/ok0115_purePatternMatching.fram | 0 test/ok/ok0116_pureRecordAccessor.fram | 0 test/ok/ok0117_comments.fram | 0 test/stdlib/stdlib0000_Int64.fram | 0 test/stdlib/stdlib0001_Option.fram | 0 test/stdlib/stdlib0002_Map.fram | 0 test/stdlib/stdlib0003_Set.fram | 0 test/stdlib/stdlib0004_Queue.fram | 0 test/test_suite | 0 313 files changed, 0 insertions(+), 0 deletions(-) mode change 100755 => 100644 .github/workflows/Test.yml mode change 100755 => 100644 .gitignore mode change 100755 => 100644 LICENSE mode change 100755 => 100644 README.md mode change 100755 => 100644 dune mode change 100755 => 100644 dune-project mode change 100755 => 100644 examples/LWT_lexical.fram mode change 100755 => 100644 examples/Modules/A.fram mode change 100755 => 100644 examples/Modules/B/A.fram mode change 100755 => 100644 examples/Modules/B/C/D.fram mode change 100755 => 100644 examples/Modules/C.fram mode change 100755 => 100644 examples/Modules/Main.fram mode change 100755 => 100644 examples/Prolog.fram mode change 100755 => 100644 examples/Pythagorean.fram mode change 100755 => 100644 examples/Tick.fram mode change 100755 => 100644 lib/Base/Assert.fram mode change 100755 => 100644 lib/Base/Bool.fram mode change 100755 => 100644 lib/Base/Char.fram mode change 100755 => 100644 lib/Base/Int.fram mode change 100755 => 100644 lib/Base/Int64.fram mode change 100755 => 100644 lib/Base/Operators.fram mode change 100755 => 100644 lib/Base/Option.fram mode change 100755 => 100644 lib/Base/String.fram mode change 100755 => 100644 lib/Base/Types.fram mode change 100755 => 100644 lib/List.fram mode change 100755 => 100644 lib/Map.fram mode change 100755 => 100644 lib/Prelude.fram mode change 100755 => 100644 lib/Queue.fram mode change 100755 => 100644 lib/RedBlackTree.fram mode change 100755 => 100644 lib/Set.fram mode change 100755 => 100644 src/DblConfig.ml mode change 100755 => 100644 src/DblParser/Desugar.ml mode change 100755 => 100644 src/DblParser/Error.ml mode change 100755 => 100644 src/DblParser/Error.mli mode change 100755 => 100644 src/DblParser/File.ml mode change 100755 => 100644 src/DblParser/File.mli mode change 100755 => 100644 src/DblParser/Import.ml mode change 100755 => 100644 src/DblParser/Import.mli mode change 100755 => 100644 src/DblParser/Lexer.mli mode change 100755 => 100644 src/DblParser/Lexer.mll mode change 100755 => 100644 src/DblParser/Main.ml mode change 100755 => 100644 src/DblParser/Main.mli mode change 100755 => 100644 src/DblParser/Raw.ml mode change 100755 => 100644 src/DblParser/YaccParser.mly mode change 100755 => 100644 src/DblParser/dune mode change 100755 => 100644 src/Eval/Env.ml mode change 100755 => 100644 src/Eval/Env.mli mode change 100755 => 100644 src/Eval/Eval.ml mode change 100755 => 100644 src/Eval/Eval.mli mode change 100755 => 100644 src/Eval/External.ml mode change 100755 => 100644 src/Eval/Value.ml mode change 100755 => 100644 src/Eval/dune mode change 100755 => 100644 src/InterpLib/Error.ml mode change 100755 => 100644 src/InterpLib/Error.mli mode change 100755 => 100644 src/InterpLib/InternalError.ml mode change 100755 => 100644 src/InterpLib/InternalError.mli mode change 100755 => 100644 src/InterpLib/TextRangePrinting.ml mode change 100755 => 100644 src/InterpLib/TextRangePrinting.mli mode change 100755 => 100644 src/InterpLib/dune mode change 100755 => 100644 src/Lang/Core.ml mode change 100755 => 100644 src/Lang/Core.mli mode change 100755 => 100644 src/Lang/CorePriv/BuiltinType.ml mode change 100755 => 100644 src/Lang/CorePriv/Effect.ml mode change 100755 => 100644 src/Lang/CorePriv/Kind.ml mode change 100755 => 100644 src/Lang/CorePriv/SExprPrinter.ml mode change 100755 => 100644 src/Lang/CorePriv/Subst.ml mode change 100755 => 100644 src/Lang/CorePriv/Subst.mli mode change 100755 => 100644 src/Lang/CorePriv/Syntax.ml mode change 100755 => 100644 src/Lang/CorePriv/Type.ml mode change 100755 => 100644 src/Lang/CorePriv/TypeBase.ml mode change 100755 => 100644 src/Lang/CorePriv/WellTypedInvariant.ml mode change 100755 => 100644 src/Lang/CorePriv/dune mode change 100755 => 100644 src/Lang/Surface.ml mode change 100755 => 100644 src/Lang/Unif.ml mode change 100755 => 100644 src/Lang/Unif.mli mode change 100755 => 100644 src/Lang/UnifPriv/BuiltinType.ml mode change 100755 => 100644 src/Lang/UnifPriv/Effect.ml mode change 100755 => 100644 src/Lang/UnifPriv/KindBase.ml mode change 100755 => 100644 src/Lang/UnifPriv/KindBase.mli mode change 100755 => 100644 src/Lang/UnifPriv/Name.ml mode change 100755 => 100644 src/Lang/UnifPriv/Scope.ml mode change 100755 => 100644 src/Lang/UnifPriv/Scope.mli mode change 100755 => 100644 src/Lang/UnifPriv/Subst.ml mode change 100755 => 100644 src/Lang/UnifPriv/Subst.mli mode change 100755 => 100644 src/Lang/UnifPriv/TVar.ml mode change 100755 => 100644 src/Lang/UnifPriv/TVar.mli mode change 100755 => 100644 src/Lang/UnifPriv/Type.ml mode change 100755 => 100644 src/Lang/UnifPriv/TypeBase.ml mode change 100755 => 100644 src/Lang/UnifPriv/TypeBase.mli mode change 100755 => 100644 src/Lang/UnifPriv/TypeWhnf.ml mode change 100755 => 100644 src/Lang/UnifPriv/dune mode change 100755 => 100644 src/Lang/Untyped.ml mode change 100755 => 100644 src/Lang/dune mode change 100755 => 100644 src/Pipeline.ml mode change 100755 => 100644 src/Pipeline.mli mode change 100755 => 100644 src/ToCore/Common.ml mode change 100755 => 100644 src/ToCore/DataType.ml mode change 100755 => 100644 src/ToCore/DataType.mli mode change 100755 => 100644 src/ToCore/Env.ml mode change 100755 => 100644 src/ToCore/Env.mli mode change 100755 => 100644 src/ToCore/Error.ml mode change 100755 => 100644 src/ToCore/Error.mli mode change 100755 => 100644 src/ToCore/Main.ml mode change 100755 => 100644 src/ToCore/Main.mli mode change 100755 => 100644 src/ToCore/PatternContext.ml mode change 100755 => 100644 src/ToCore/PatternMatch.ml mode change 100755 => 100644 src/ToCore/PatternMatch.mli mode change 100755 => 100644 src/ToCore/Type.ml mode change 100755 => 100644 src/ToCore/dune mode change 100755 => 100644 src/TypeErase.ml mode change 100755 => 100644 src/TypeInference/Common.ml mode change 100755 => 100644 src/TypeInference/DataType.ml mode change 100755 => 100644 src/TypeInference/DataType.mli mode change 100755 => 100644 src/TypeInference/Def.ml mode change 100755 => 100644 src/TypeInference/Def.mli mode change 100755 => 100644 src/TypeInference/Env.ml mode change 100755 => 100644 src/TypeInference/Env.mli mode change 100755 => 100644 src/TypeInference/Error.ml mode change 100755 => 100644 src/TypeInference/Error.mli mode change 100755 => 100644 src/TypeInference/Expr.ml mode change 100755 => 100644 src/TypeInference/Expr.mli mode change 100755 => 100644 src/TypeInference/ExprUtils.ml mode change 100755 => 100644 src/TypeInference/ExprUtils.mli mode change 100755 => 100644 src/TypeInference/ImplicitEnv.ml mode change 100755 => 100644 src/TypeInference/ImplicitEnv.mli mode change 100755 => 100644 src/TypeInference/Main.ml mode change 100755 => 100644 src/TypeInference/Main.mli mode change 100755 => 100644 src/TypeInference/MatchClause.ml mode change 100755 => 100644 src/TypeInference/MatchClause.mli mode change 100755 => 100644 src/TypeInference/ModStack.ml mode change 100755 => 100644 src/TypeInference/ModStack.mli mode change 100755 => 100644 src/TypeInference/Module.ml mode change 100755 => 100644 src/TypeInference/Module.mli mode change 100755 => 100644 src/TypeInference/Name.ml mode change 100755 => 100644 src/TypeInference/Name.mli mode change 100755 => 100644 src/TypeInference/Pattern.ml mode change 100755 => 100644 src/TypeInference/Pattern.mli mode change 100755 => 100644 src/TypeInference/PolyExpr.ml mode change 100755 => 100644 src/TypeInference/PolyExpr.mli mode change 100755 => 100644 src/TypeInference/PreludeTypes.ml mode change 100755 => 100644 src/TypeInference/PreludeTypes.mli mode change 100755 => 100644 src/TypeInference/Pretty.ml mode change 100755 => 100644 src/TypeInference/Pretty.mli mode change 100755 => 100644 src/TypeInference/RecDefs.ml mode change 100755 => 100644 src/TypeInference/RecDefs.mli mode change 100755 => 100644 src/TypeInference/Type.ml mode change 100755 => 100644 src/TypeInference/Type.mli mode change 100755 => 100644 src/TypeInference/TypeCheckFix.ml mode change 100755 => 100644 src/TypeInference/TypeHints.ml mode change 100755 => 100644 src/TypeInference/TypeHints.mli mode change 100755 => 100644 src/TypeInference/TypeUtils.ml mode change 100755 => 100644 src/TypeInference/TypeUtils.mli mode change 100755 => 100644 src/TypeInference/Unification.ml mode change 100755 => 100644 src/TypeInference/Unification.mli mode change 100755 => 100644 src/TypeInference/Uniqueness.ml mode change 100755 => 100644 src/TypeInference/Uniqueness.mli mode change 100755 => 100644 src/TypeInference/dune mode change 100755 => 100644 src/Utils/BRef.ml mode change 100755 => 100644 src/Utils/BRef.mli mode change 100755 => 100644 src/Utils/Eq.ml mode change 100755 => 100644 src/Utils/Map1.ml mode change 100755 => 100644 src/Utils/Perm.ml mode change 100755 => 100644 src/Utils/Position.ml mode change 100755 => 100644 src/Utils/SExpr.ml mode change 100755 => 100644 src/Utils/SExpr.mli mode change 100755 => 100644 src/Utils/SyntaxNode.ml mode change 100755 => 100644 src/Utils/UID.ml mode change 100755 => 100644 src/Utils/UID.mli mode change 100755 => 100644 src/Utils/Var.ml mode change 100755 => 100644 src/Utils/Var.mli mode change 100755 => 100644 src/Utils/dune mode change 100755 => 100644 src/dbl.ml mode change 100755 => 100644 src/dune mode change 100755 => 100644 test/err/lexer_0000_illegalOp0.fram mode change 100755 => 100644 test/err/lexer_0001_illegalOp1.fram mode change 100755 => 100644 test/err/lexer_0002_eofInComment.fram mode change 100755 => 100644 test/err/parser_0000_illegalBinopPattern.fram mode change 100755 => 100644 test/err/parser_0001_illegalBinopCtor.fram mode change 100755 => 100644 test/err/parser_0002_illegalBinopMethod.fram mode change 100755 => 100644 test/err/tc_0000_implicitLoop.fram mode change 100755 => 100644 test/err/tc_0001_escapingType.fram mode change 100755 => 100644 test/err/tc_0002_escapingType.fram mode change 100755 => 100644 test/err/tc_0004_methodFn.fram mode change 100755 => 100644 test/err/tc_0005_specialBinops.fram mode change 100755 => 100644 test/err/tc_0006_unapplicableKind.fram mode change 100755 => 100644 test/err/tc_0007_missingOptionTypeDef.fram mode change 100755 => 100644 test/err/tc_0008_invalidOptionTypeConstructors.fram mode change 100755 => 100644 test/err/tc_0009_polymorphicOptionalArg.fram mode change 100755 => 100644 test/err/tc_0010_impureNonPositiveRecord.fram mode change 100755 => 100644 test/err/tc_0011_nonPositiveUVar.fram mode change 100755 => 100644 test/err/tc_0012_impureExprInPureMatch.fram mode change 100755 => 100644 test/ok/ok0000_emptyFile.fram mode change 100755 => 100644 test/ok/ok0001_id.fram mode change 100755 => 100644 test/ok/ok0002_poly.fram mode change 100755 => 100644 test/ok/ok0003_local.fram mode change 100755 => 100644 test/ok/ok0004_fnArg.fram mode change 100755 => 100644 test/ok/ok0005_let.fram mode change 100755 => 100644 test/ok/ok0006_fnArg.fram mode change 100755 => 100644 test/ok/ok0007_letArg.fram mode change 100755 => 100644 test/ok/ok0008_idHandler.fram mode change 100755 => 100644 test/ok/ok0009_purityRestriction.fram mode change 100755 => 100644 test/ok/ok0010_implicit.fram mode change 100755 => 100644 test/ok/ok0011_implicit.fram mode change 100755 => 100644 test/ok/ok0012_adt.fram mode change 100755 => 100644 test/ok/ok0013_emptyADT.fram mode change 100755 => 100644 test/ok/ok0014_arrows.fram mode change 100755 => 100644 test/ok/ok0015_ctor.fram mode change 100755 => 100644 test/ok/ok0016_trivialMatch.fram mode change 100755 => 100644 test/ok/ok0017_wildcard.fram mode change 100755 => 100644 test/ok/ok0018_namePattern.fram mode change 100755 => 100644 test/ok/ok0019_simplePattern.fram mode change 100755 => 100644 test/ok/ok0020_patternMatch.fram mode change 100755 => 100644 test/ok/ok0021_simpleMatch.fram mode change 100755 => 100644 test/ok/ok0022_deepMatch.fram mode change 100755 => 100644 test/ok/ok0023_letPattern.fram mode change 100755 => 100644 test/ok/ok0024_letFunc.fram mode change 100755 => 100644 test/ok/ok0025_letFuncImplicit.fram mode change 100755 => 100644 test/ok/ok0026_funSugar.fram mode change 100755 => 100644 test/ok/ok0027_explicitApp.fram mode change 100755 => 100644 test/ok/ok0028_patArg.fram mode change 100755 => 100644 test/ok/ok0029_handle.fram mode change 100755 => 100644 test/ok/ok0030_bt.fram mode change 100755 => 100644 test/ok/ok0031_explicitArg.fram mode change 100755 => 100644 test/ok/ok0032_dataArg.fram mode change 100755 => 100644 test/ok/ok0033_higherKinds.fram mode change 100755 => 100644 test/ok/ok0034_schemes.fram mode change 100755 => 100644 test/ok/ok0035_schemes.fram mode change 100755 => 100644 test/ok/ok0036_schemeAnnot.fram mode change 100755 => 100644 test/ok/ok0037_checkScheme.fram mode change 100755 => 100644 test/ok/ok0038_explicitArg.fram mode change 100755 => 100644 test/ok/ok0039_polymorphicImplicit.fram mode change 100755 => 100644 test/ok/ok0040_polymorphicFields.fram mode change 100755 => 100644 test/ok/ok0041_existentialTypes.fram mode change 100755 => 100644 test/ok/ok0042_existentialTypes.fram mode change 100755 => 100644 test/ok/ok0043_implicitCtorArgs.fram mode change 100755 => 100644 test/ok/ok0044_implicitCtorArgs.fram mode change 100755 => 100644 test/ok/ok0045_recursiveData.fram mode change 100755 => 100644 test/ok/ok0046_mutualDataRec.fram mode change 100755 => 100644 test/ok/ok0047_namedParam.fram mode change 100755 => 100644 test/ok/ok0048_explicitTypeInst.fram mode change 100755 => 100644 test/ok/ok0049_expilicitInstOrder.fram mode change 100755 => 100644 test/ok/ok0050_typeArgRename.fram mode change 100755 => 100644 test/ok/ok0051_existentialTypePattern.fram mode change 100755 => 100644 test/ok/ok0052_emptyMatch.fram mode change 100755 => 100644 test/ok/ok0053_firstClassHandler.fram mode change 100755 => 100644 test/ok/ok0054_firstClassHandler.fram mode change 100755 => 100644 test/ok/ok0055_complexHandlers.fram mode change 100755 => 100644 test/ok/ok0056_complexHandlers.fram mode change 100755 => 100644 test/ok/ok0057_dataArgLabels.fram mode change 100755 => 100644 test/ok/ok0058_unitState.fram mode change 100755 => 100644 test/ok/ok0059_effectArg.fram mode change 100755 => 100644 test/ok/ok0060_returnFinally.fram mode change 100755 => 100644 test/ok/ok0061_returnFinallyMatch.fram mode change 100755 => 100644 test/ok/ok0062_theLabel.fram mode change 100755 => 100644 test/ok/ok0064_typeAnnot.fram mode change 100755 => 100644 test/ok/ok0066_method.fram mode change 100755 => 100644 test/ok/ok0067_pureMethod.fram mode change 100755 => 100644 test/ok/ok0068_shadowCtors.fram mode change 100755 => 100644 test/ok/ok0069_effectCtorArg.fram mode change 100755 => 100644 test/ok/ok0070_effectMethodArg.fram mode change 100755 => 100644 test/ok/ok0071_numbers.fram mode change 100755 => 100644 test/ok/ok0072_strings.fram mode change 100755 => 100644 test/ok/ok0073_extern.fram mode change 100755 => 100644 test/ok/ok0074_implicitWithType.fram mode change 100755 => 100644 test/ok/ok0075_effectsFromImplicits.fram mode change 100755 => 100644 test/ok/ok0076_ifExpr.fram mode change 100755 => 100644 test/ok/ok0077_effectResume.fram mode change 100755 => 100644 test/ok/ok0078_unitMethods.fram mode change 100755 => 100644 test/ok/ok0079_impureMethod.fram mode change 100755 => 100644 test/ok/ok0080_moduleDef.fram mode change 100755 => 100644 test/ok/ok0081_nestedModule.fram mode change 100755 => 100644 test/ok/ok0082_moduleDataDef.fram mode change 100755 => 100644 test/ok/ok0083_pubPatternMatch.fram mode change 100755 => 100644 test/ok/ok0084_operators.fram mode change 100755 => 100644 test/ok/ok0085_letChecked.fram mode change 100755 => 100644 test/ok/ok0086_optionState.fram mode change 100755 => 100644 test/ok/ok0087_opratorOverloading.fram mode change 100755 => 100644 test/ok/ok0088_abstractData.fram mode change 100755 => 100644 test/ok/ok0089_pubPat.fram mode change 100755 => 100644 test/ok/ok0090_lists.fram mode change 100755 => 100644 test/ok/ok0091_namedParamMethod.fram mode change 100755 => 100644 test/ok/ok0092_multipleNamedMethodParams.fram mode change 100755 => 100644 test/ok/ok0093_specialBinops.fram mode change 100755 => 100644 test/ok/ok0094_unaryIf.fram mode change 100755 => 100644 test/ok/ok0095_wildcardTypeParam.fram mode change 100755 => 100644 test/ok/ok0096_fixTypeAnnot.fram mode change 100755 => 100644 test/ok/ok0097_recursion.fram mode change 100755 => 100644 test/ok/ok0098_mutualRecursion.fram mode change 100755 => 100644 test/ok/ok0099_nestedEffArrows.fram mode change 100755 => 100644 test/ok/ok0100_polymorphicRecursion.fram mode change 100755 => 100644 test/ok/ok0101_implicitParamsRecord.fram mode change 100755 => 100644 test/ok/ok0102_simpleRecord.fram mode change 100755 => 100644 test/ok/ok0103_genericRecords.fram mode change 100755 => 100644 test/ok/ok0104_chars.fram mode change 100755 => 100644 test/ok/ok0105_recFunWithNamedParam.fram mode change 100755 => 100644 test/ok/ok0106_recursiveMethod.fram mode change 100755 => 100644 test/ok/ok0107_polymorphicRecursion.fram mode change 100755 => 100644 test/ok/ok0108_modulePattern.fram mode change 100755 => 100644 test/ok/ok0109_fieldPattern.fram mode change 100755 => 100644 test/ok/ok0110_publicModulePattern.fram mode change 100755 => 100644 test/ok/ok0111_optionalParams.fram mode change 100755 => 100644 test/ok/ok0112_pureRecord.fram mode change 100755 => 100644 test/ok/ok0113_pureMatchingNonrecUVar.fram mode change 100755 => 100644 test/ok/ok0114_pureTail.fram mode change 100755 => 100644 test/ok/ok0115_purePatternMatching.fram mode change 100755 => 100644 test/ok/ok0116_pureRecordAccessor.fram mode change 100755 => 100644 test/ok/ok0117_comments.fram mode change 100755 => 100644 test/stdlib/stdlib0000_Int64.fram mode change 100755 => 100644 test/stdlib/stdlib0001_Option.fram mode change 100755 => 100644 test/stdlib/stdlib0002_Map.fram mode change 100755 => 100644 test/stdlib/stdlib0003_Set.fram mode change 100755 => 100644 test/stdlib/stdlib0004_Queue.fram mode change 100755 => 100644 test/test_suite diff --git a/.github/workflows/Test.yml b/.github/workflows/Test.yml old mode 100755 new mode 100644 diff --git a/.gitignore b/.gitignore old mode 100755 new mode 100644 diff --git a/LICENSE b/LICENSE old mode 100755 new mode 100644 diff --git a/README.md b/README.md old mode 100755 new mode 100644 diff --git a/dune b/dune old mode 100755 new mode 100644 diff --git a/dune-project b/dune-project old mode 100755 new mode 100644 diff --git a/examples/LWT_lexical.fram b/examples/LWT_lexical.fram old mode 100755 new mode 100644 diff --git a/examples/Modules/A.fram b/examples/Modules/A.fram old mode 100755 new mode 100644 diff --git a/examples/Modules/B/A.fram b/examples/Modules/B/A.fram old mode 100755 new mode 100644 diff --git a/examples/Modules/B/C/D.fram b/examples/Modules/B/C/D.fram old mode 100755 new mode 100644 diff --git a/examples/Modules/C.fram b/examples/Modules/C.fram old mode 100755 new mode 100644 diff --git a/examples/Modules/Main.fram b/examples/Modules/Main.fram old mode 100755 new mode 100644 diff --git a/examples/Prolog.fram b/examples/Prolog.fram old mode 100755 new mode 100644 diff --git a/examples/Pythagorean.fram b/examples/Pythagorean.fram old mode 100755 new mode 100644 diff --git a/examples/Tick.fram b/examples/Tick.fram old mode 100755 new mode 100644 diff --git a/lib/Base/Assert.fram b/lib/Base/Assert.fram old mode 100755 new mode 100644 diff --git a/lib/Base/Bool.fram b/lib/Base/Bool.fram old mode 100755 new mode 100644 diff --git a/lib/Base/Char.fram b/lib/Base/Char.fram old mode 100755 new mode 100644 diff --git a/lib/Base/Int.fram b/lib/Base/Int.fram old mode 100755 new mode 100644 diff --git a/lib/Base/Int64.fram b/lib/Base/Int64.fram old mode 100755 new mode 100644 diff --git a/lib/Base/Operators.fram b/lib/Base/Operators.fram old mode 100755 new mode 100644 diff --git a/lib/Base/Option.fram b/lib/Base/Option.fram old mode 100755 new mode 100644 diff --git a/lib/Base/String.fram b/lib/Base/String.fram old mode 100755 new mode 100644 diff --git a/lib/Base/Types.fram b/lib/Base/Types.fram old mode 100755 new mode 100644 diff --git a/lib/List.fram b/lib/List.fram old mode 100755 new mode 100644 diff --git a/lib/Map.fram b/lib/Map.fram old mode 100755 new mode 100644 diff --git a/lib/Prelude.fram b/lib/Prelude.fram old mode 100755 new mode 100644 diff --git a/lib/Queue.fram b/lib/Queue.fram old mode 100755 new mode 100644 diff --git a/lib/RedBlackTree.fram b/lib/RedBlackTree.fram old mode 100755 new mode 100644 diff --git a/lib/Set.fram b/lib/Set.fram old mode 100755 new mode 100644 diff --git a/src/DblConfig.ml b/src/DblConfig.ml old mode 100755 new mode 100644 diff --git a/src/DblParser/Desugar.ml b/src/DblParser/Desugar.ml old mode 100755 new mode 100644 diff --git a/src/DblParser/Error.ml b/src/DblParser/Error.ml old mode 100755 new mode 100644 diff --git a/src/DblParser/Error.mli b/src/DblParser/Error.mli old mode 100755 new mode 100644 diff --git a/src/DblParser/File.ml b/src/DblParser/File.ml old mode 100755 new mode 100644 diff --git a/src/DblParser/File.mli b/src/DblParser/File.mli old mode 100755 new mode 100644 diff --git a/src/DblParser/Import.ml b/src/DblParser/Import.ml old mode 100755 new mode 100644 diff --git a/src/DblParser/Import.mli b/src/DblParser/Import.mli old mode 100755 new mode 100644 diff --git a/src/DblParser/Lexer.mli b/src/DblParser/Lexer.mli old mode 100755 new mode 100644 diff --git a/src/DblParser/Lexer.mll b/src/DblParser/Lexer.mll old mode 100755 new mode 100644 diff --git a/src/DblParser/Main.ml b/src/DblParser/Main.ml old mode 100755 new mode 100644 diff --git a/src/DblParser/Main.mli b/src/DblParser/Main.mli old mode 100755 new mode 100644 diff --git a/src/DblParser/Raw.ml b/src/DblParser/Raw.ml old mode 100755 new mode 100644 diff --git a/src/DblParser/YaccParser.mly b/src/DblParser/YaccParser.mly old mode 100755 new mode 100644 diff --git a/src/DblParser/dune b/src/DblParser/dune old mode 100755 new mode 100644 diff --git a/src/Eval/Env.ml b/src/Eval/Env.ml old mode 100755 new mode 100644 diff --git a/src/Eval/Env.mli b/src/Eval/Env.mli old mode 100755 new mode 100644 diff --git a/src/Eval/Eval.ml b/src/Eval/Eval.ml old mode 100755 new mode 100644 diff --git a/src/Eval/Eval.mli b/src/Eval/Eval.mli old mode 100755 new mode 100644 diff --git a/src/Eval/External.ml b/src/Eval/External.ml old mode 100755 new mode 100644 diff --git a/src/Eval/Value.ml b/src/Eval/Value.ml old mode 100755 new mode 100644 diff --git a/src/Eval/dune b/src/Eval/dune old mode 100755 new mode 100644 diff --git a/src/InterpLib/Error.ml b/src/InterpLib/Error.ml old mode 100755 new mode 100644 diff --git a/src/InterpLib/Error.mli b/src/InterpLib/Error.mli old mode 100755 new mode 100644 diff --git a/src/InterpLib/InternalError.ml b/src/InterpLib/InternalError.ml old mode 100755 new mode 100644 diff --git a/src/InterpLib/InternalError.mli b/src/InterpLib/InternalError.mli old mode 100755 new mode 100644 diff --git a/src/InterpLib/TextRangePrinting.ml b/src/InterpLib/TextRangePrinting.ml old mode 100755 new mode 100644 diff --git a/src/InterpLib/TextRangePrinting.mli b/src/InterpLib/TextRangePrinting.mli old mode 100755 new mode 100644 diff --git a/src/InterpLib/dune b/src/InterpLib/dune old mode 100755 new mode 100644 diff --git a/src/Lang/Core.ml b/src/Lang/Core.ml old mode 100755 new mode 100644 diff --git a/src/Lang/Core.mli b/src/Lang/Core.mli old mode 100755 new mode 100644 diff --git a/src/Lang/CorePriv/BuiltinType.ml b/src/Lang/CorePriv/BuiltinType.ml old mode 100755 new mode 100644 diff --git a/src/Lang/CorePriv/Effect.ml b/src/Lang/CorePriv/Effect.ml old mode 100755 new mode 100644 diff --git a/src/Lang/CorePriv/Kind.ml b/src/Lang/CorePriv/Kind.ml old mode 100755 new mode 100644 diff --git a/src/Lang/CorePriv/SExprPrinter.ml b/src/Lang/CorePriv/SExprPrinter.ml old mode 100755 new mode 100644 diff --git a/src/Lang/CorePriv/Subst.ml b/src/Lang/CorePriv/Subst.ml old mode 100755 new mode 100644 diff --git a/src/Lang/CorePriv/Subst.mli b/src/Lang/CorePriv/Subst.mli old mode 100755 new mode 100644 diff --git a/src/Lang/CorePriv/Syntax.ml b/src/Lang/CorePriv/Syntax.ml old mode 100755 new mode 100644 diff --git a/src/Lang/CorePriv/Type.ml b/src/Lang/CorePriv/Type.ml old mode 100755 new mode 100644 diff --git a/src/Lang/CorePriv/TypeBase.ml b/src/Lang/CorePriv/TypeBase.ml old mode 100755 new mode 100644 diff --git a/src/Lang/CorePriv/WellTypedInvariant.ml b/src/Lang/CorePriv/WellTypedInvariant.ml old mode 100755 new mode 100644 diff --git a/src/Lang/CorePriv/dune b/src/Lang/CorePriv/dune old mode 100755 new mode 100644 diff --git a/src/Lang/Surface.ml b/src/Lang/Surface.ml old mode 100755 new mode 100644 diff --git a/src/Lang/Unif.ml b/src/Lang/Unif.ml old mode 100755 new mode 100644 diff --git a/src/Lang/Unif.mli b/src/Lang/Unif.mli old mode 100755 new mode 100644 diff --git a/src/Lang/UnifPriv/BuiltinType.ml b/src/Lang/UnifPriv/BuiltinType.ml old mode 100755 new mode 100644 diff --git a/src/Lang/UnifPriv/Effect.ml b/src/Lang/UnifPriv/Effect.ml old mode 100755 new mode 100644 diff --git a/src/Lang/UnifPriv/KindBase.ml b/src/Lang/UnifPriv/KindBase.ml old mode 100755 new mode 100644 diff --git a/src/Lang/UnifPriv/KindBase.mli b/src/Lang/UnifPriv/KindBase.mli old mode 100755 new mode 100644 diff --git a/src/Lang/UnifPriv/Name.ml b/src/Lang/UnifPriv/Name.ml old mode 100755 new mode 100644 diff --git a/src/Lang/UnifPriv/Scope.ml b/src/Lang/UnifPriv/Scope.ml old mode 100755 new mode 100644 diff --git a/src/Lang/UnifPriv/Scope.mli b/src/Lang/UnifPriv/Scope.mli old mode 100755 new mode 100644 diff --git a/src/Lang/UnifPriv/Subst.ml b/src/Lang/UnifPriv/Subst.ml old mode 100755 new mode 100644 diff --git a/src/Lang/UnifPriv/Subst.mli b/src/Lang/UnifPriv/Subst.mli old mode 100755 new mode 100644 diff --git a/src/Lang/UnifPriv/TVar.ml b/src/Lang/UnifPriv/TVar.ml old mode 100755 new mode 100644 diff --git a/src/Lang/UnifPriv/TVar.mli b/src/Lang/UnifPriv/TVar.mli old mode 100755 new mode 100644 diff --git a/src/Lang/UnifPriv/Type.ml b/src/Lang/UnifPriv/Type.ml old mode 100755 new mode 100644 diff --git a/src/Lang/UnifPriv/TypeBase.ml b/src/Lang/UnifPriv/TypeBase.ml old mode 100755 new mode 100644 diff --git a/src/Lang/UnifPriv/TypeBase.mli b/src/Lang/UnifPriv/TypeBase.mli old mode 100755 new mode 100644 diff --git a/src/Lang/UnifPriv/TypeWhnf.ml b/src/Lang/UnifPriv/TypeWhnf.ml old mode 100755 new mode 100644 diff --git a/src/Lang/UnifPriv/dune b/src/Lang/UnifPriv/dune old mode 100755 new mode 100644 diff --git a/src/Lang/Untyped.ml b/src/Lang/Untyped.ml old mode 100755 new mode 100644 diff --git a/src/Lang/dune b/src/Lang/dune old mode 100755 new mode 100644 diff --git a/src/Pipeline.ml b/src/Pipeline.ml old mode 100755 new mode 100644 diff --git a/src/Pipeline.mli b/src/Pipeline.mli old mode 100755 new mode 100644 diff --git a/src/ToCore/Common.ml b/src/ToCore/Common.ml old mode 100755 new mode 100644 diff --git a/src/ToCore/DataType.ml b/src/ToCore/DataType.ml old mode 100755 new mode 100644 diff --git a/src/ToCore/DataType.mli b/src/ToCore/DataType.mli old mode 100755 new mode 100644 diff --git a/src/ToCore/Env.ml b/src/ToCore/Env.ml old mode 100755 new mode 100644 diff --git a/src/ToCore/Env.mli b/src/ToCore/Env.mli old mode 100755 new mode 100644 diff --git a/src/ToCore/Error.ml b/src/ToCore/Error.ml old mode 100755 new mode 100644 diff --git a/src/ToCore/Error.mli b/src/ToCore/Error.mli old mode 100755 new mode 100644 diff --git a/src/ToCore/Main.ml b/src/ToCore/Main.ml old mode 100755 new mode 100644 diff --git a/src/ToCore/Main.mli b/src/ToCore/Main.mli old mode 100755 new mode 100644 diff --git a/src/ToCore/PatternContext.ml b/src/ToCore/PatternContext.ml old mode 100755 new mode 100644 diff --git a/src/ToCore/PatternMatch.ml b/src/ToCore/PatternMatch.ml old mode 100755 new mode 100644 diff --git a/src/ToCore/PatternMatch.mli b/src/ToCore/PatternMatch.mli old mode 100755 new mode 100644 diff --git a/src/ToCore/Type.ml b/src/ToCore/Type.ml old mode 100755 new mode 100644 diff --git a/src/ToCore/dune b/src/ToCore/dune old mode 100755 new mode 100644 diff --git a/src/TypeErase.ml b/src/TypeErase.ml old mode 100755 new mode 100644 diff --git a/src/TypeInference/Common.ml b/src/TypeInference/Common.ml old mode 100755 new mode 100644 diff --git a/src/TypeInference/DataType.ml b/src/TypeInference/DataType.ml old mode 100755 new mode 100644 diff --git a/src/TypeInference/DataType.mli b/src/TypeInference/DataType.mli old mode 100755 new mode 100644 diff --git a/src/TypeInference/Def.ml b/src/TypeInference/Def.ml old mode 100755 new mode 100644 diff --git a/src/TypeInference/Def.mli b/src/TypeInference/Def.mli old mode 100755 new mode 100644 diff --git a/src/TypeInference/Env.ml b/src/TypeInference/Env.ml old mode 100755 new mode 100644 diff --git a/src/TypeInference/Env.mli b/src/TypeInference/Env.mli old mode 100755 new mode 100644 diff --git a/src/TypeInference/Error.ml b/src/TypeInference/Error.ml old mode 100755 new mode 100644 diff --git a/src/TypeInference/Error.mli b/src/TypeInference/Error.mli old mode 100755 new mode 100644 diff --git a/src/TypeInference/Expr.ml b/src/TypeInference/Expr.ml old mode 100755 new mode 100644 diff --git a/src/TypeInference/Expr.mli b/src/TypeInference/Expr.mli old mode 100755 new mode 100644 diff --git a/src/TypeInference/ExprUtils.ml b/src/TypeInference/ExprUtils.ml old mode 100755 new mode 100644 diff --git a/src/TypeInference/ExprUtils.mli b/src/TypeInference/ExprUtils.mli old mode 100755 new mode 100644 diff --git a/src/TypeInference/ImplicitEnv.ml b/src/TypeInference/ImplicitEnv.ml old mode 100755 new mode 100644 diff --git a/src/TypeInference/ImplicitEnv.mli b/src/TypeInference/ImplicitEnv.mli old mode 100755 new mode 100644 diff --git a/src/TypeInference/Main.ml b/src/TypeInference/Main.ml old mode 100755 new mode 100644 diff --git a/src/TypeInference/Main.mli b/src/TypeInference/Main.mli old mode 100755 new mode 100644 diff --git a/src/TypeInference/MatchClause.ml b/src/TypeInference/MatchClause.ml old mode 100755 new mode 100644 diff --git a/src/TypeInference/MatchClause.mli b/src/TypeInference/MatchClause.mli old mode 100755 new mode 100644 diff --git a/src/TypeInference/ModStack.ml b/src/TypeInference/ModStack.ml old mode 100755 new mode 100644 diff --git a/src/TypeInference/ModStack.mli b/src/TypeInference/ModStack.mli old mode 100755 new mode 100644 diff --git a/src/TypeInference/Module.ml b/src/TypeInference/Module.ml old mode 100755 new mode 100644 diff --git a/src/TypeInference/Module.mli b/src/TypeInference/Module.mli old mode 100755 new mode 100644 diff --git a/src/TypeInference/Name.ml b/src/TypeInference/Name.ml old mode 100755 new mode 100644 diff --git a/src/TypeInference/Name.mli b/src/TypeInference/Name.mli old mode 100755 new mode 100644 diff --git a/src/TypeInference/Pattern.ml b/src/TypeInference/Pattern.ml old mode 100755 new mode 100644 diff --git a/src/TypeInference/Pattern.mli b/src/TypeInference/Pattern.mli old mode 100755 new mode 100644 diff --git a/src/TypeInference/PolyExpr.ml b/src/TypeInference/PolyExpr.ml old mode 100755 new mode 100644 diff --git a/src/TypeInference/PolyExpr.mli b/src/TypeInference/PolyExpr.mli old mode 100755 new mode 100644 diff --git a/src/TypeInference/PreludeTypes.ml b/src/TypeInference/PreludeTypes.ml old mode 100755 new mode 100644 diff --git a/src/TypeInference/PreludeTypes.mli b/src/TypeInference/PreludeTypes.mli old mode 100755 new mode 100644 diff --git a/src/TypeInference/Pretty.ml b/src/TypeInference/Pretty.ml old mode 100755 new mode 100644 diff --git a/src/TypeInference/Pretty.mli b/src/TypeInference/Pretty.mli old mode 100755 new mode 100644 diff --git a/src/TypeInference/RecDefs.ml b/src/TypeInference/RecDefs.ml old mode 100755 new mode 100644 diff --git a/src/TypeInference/RecDefs.mli b/src/TypeInference/RecDefs.mli old mode 100755 new mode 100644 diff --git a/src/TypeInference/Type.ml b/src/TypeInference/Type.ml old mode 100755 new mode 100644 diff --git a/src/TypeInference/Type.mli b/src/TypeInference/Type.mli old mode 100755 new mode 100644 diff --git a/src/TypeInference/TypeCheckFix.ml b/src/TypeInference/TypeCheckFix.ml old mode 100755 new mode 100644 diff --git a/src/TypeInference/TypeHints.ml b/src/TypeInference/TypeHints.ml old mode 100755 new mode 100644 diff --git a/src/TypeInference/TypeHints.mli b/src/TypeInference/TypeHints.mli old mode 100755 new mode 100644 diff --git a/src/TypeInference/TypeUtils.ml b/src/TypeInference/TypeUtils.ml old mode 100755 new mode 100644 diff --git a/src/TypeInference/TypeUtils.mli b/src/TypeInference/TypeUtils.mli old mode 100755 new mode 100644 diff --git a/src/TypeInference/Unification.ml b/src/TypeInference/Unification.ml old mode 100755 new mode 100644 diff --git a/src/TypeInference/Unification.mli b/src/TypeInference/Unification.mli old mode 100755 new mode 100644 diff --git a/src/TypeInference/Uniqueness.ml b/src/TypeInference/Uniqueness.ml old mode 100755 new mode 100644 diff --git a/src/TypeInference/Uniqueness.mli b/src/TypeInference/Uniqueness.mli old mode 100755 new mode 100644 diff --git a/src/TypeInference/dune b/src/TypeInference/dune old mode 100755 new mode 100644 diff --git a/src/Utils/BRef.ml b/src/Utils/BRef.ml old mode 100755 new mode 100644 diff --git a/src/Utils/BRef.mli b/src/Utils/BRef.mli old mode 100755 new mode 100644 diff --git a/src/Utils/Eq.ml b/src/Utils/Eq.ml old mode 100755 new mode 100644 diff --git a/src/Utils/Map1.ml b/src/Utils/Map1.ml old mode 100755 new mode 100644 diff --git a/src/Utils/Perm.ml b/src/Utils/Perm.ml old mode 100755 new mode 100644 diff --git a/src/Utils/Position.ml b/src/Utils/Position.ml old mode 100755 new mode 100644 diff --git a/src/Utils/SExpr.ml b/src/Utils/SExpr.ml old mode 100755 new mode 100644 diff --git a/src/Utils/SExpr.mli b/src/Utils/SExpr.mli old mode 100755 new mode 100644 diff --git a/src/Utils/SyntaxNode.ml b/src/Utils/SyntaxNode.ml old mode 100755 new mode 100644 diff --git a/src/Utils/UID.ml b/src/Utils/UID.ml old mode 100755 new mode 100644 diff --git a/src/Utils/UID.mli b/src/Utils/UID.mli old mode 100755 new mode 100644 diff --git a/src/Utils/Var.ml b/src/Utils/Var.ml old mode 100755 new mode 100644 diff --git a/src/Utils/Var.mli b/src/Utils/Var.mli old mode 100755 new mode 100644 diff --git a/src/Utils/dune b/src/Utils/dune old mode 100755 new mode 100644 diff --git a/src/dbl.ml b/src/dbl.ml old mode 100755 new mode 100644 diff --git a/src/dune b/src/dune old mode 100755 new mode 100644 diff --git a/test/err/lexer_0000_illegalOp0.fram b/test/err/lexer_0000_illegalOp0.fram old mode 100755 new mode 100644 diff --git a/test/err/lexer_0001_illegalOp1.fram b/test/err/lexer_0001_illegalOp1.fram old mode 100755 new mode 100644 diff --git a/test/err/lexer_0002_eofInComment.fram b/test/err/lexer_0002_eofInComment.fram old mode 100755 new mode 100644 diff --git a/test/err/parser_0000_illegalBinopPattern.fram b/test/err/parser_0000_illegalBinopPattern.fram old mode 100755 new mode 100644 diff --git a/test/err/parser_0001_illegalBinopCtor.fram b/test/err/parser_0001_illegalBinopCtor.fram old mode 100755 new mode 100644 diff --git a/test/err/parser_0002_illegalBinopMethod.fram b/test/err/parser_0002_illegalBinopMethod.fram old mode 100755 new mode 100644 diff --git a/test/err/tc_0000_implicitLoop.fram b/test/err/tc_0000_implicitLoop.fram old mode 100755 new mode 100644 diff --git a/test/err/tc_0001_escapingType.fram b/test/err/tc_0001_escapingType.fram old mode 100755 new mode 100644 diff --git a/test/err/tc_0002_escapingType.fram b/test/err/tc_0002_escapingType.fram old mode 100755 new mode 100644 diff --git a/test/err/tc_0004_methodFn.fram b/test/err/tc_0004_methodFn.fram old mode 100755 new mode 100644 diff --git a/test/err/tc_0005_specialBinops.fram b/test/err/tc_0005_specialBinops.fram old mode 100755 new mode 100644 diff --git a/test/err/tc_0006_unapplicableKind.fram b/test/err/tc_0006_unapplicableKind.fram old mode 100755 new mode 100644 diff --git a/test/err/tc_0007_missingOptionTypeDef.fram b/test/err/tc_0007_missingOptionTypeDef.fram old mode 100755 new mode 100644 diff --git a/test/err/tc_0008_invalidOptionTypeConstructors.fram b/test/err/tc_0008_invalidOptionTypeConstructors.fram old mode 100755 new mode 100644 diff --git a/test/err/tc_0009_polymorphicOptionalArg.fram b/test/err/tc_0009_polymorphicOptionalArg.fram old mode 100755 new mode 100644 diff --git a/test/err/tc_0010_impureNonPositiveRecord.fram b/test/err/tc_0010_impureNonPositiveRecord.fram old mode 100755 new mode 100644 diff --git a/test/err/tc_0011_nonPositiveUVar.fram b/test/err/tc_0011_nonPositiveUVar.fram old mode 100755 new mode 100644 diff --git a/test/err/tc_0012_impureExprInPureMatch.fram b/test/err/tc_0012_impureExprInPureMatch.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0000_emptyFile.fram b/test/ok/ok0000_emptyFile.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0001_id.fram b/test/ok/ok0001_id.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0002_poly.fram b/test/ok/ok0002_poly.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0003_local.fram b/test/ok/ok0003_local.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0004_fnArg.fram b/test/ok/ok0004_fnArg.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0005_let.fram b/test/ok/ok0005_let.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0006_fnArg.fram b/test/ok/ok0006_fnArg.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0007_letArg.fram b/test/ok/ok0007_letArg.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0008_idHandler.fram b/test/ok/ok0008_idHandler.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0009_purityRestriction.fram b/test/ok/ok0009_purityRestriction.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0010_implicit.fram b/test/ok/ok0010_implicit.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0011_implicit.fram b/test/ok/ok0011_implicit.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0012_adt.fram b/test/ok/ok0012_adt.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0013_emptyADT.fram b/test/ok/ok0013_emptyADT.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0014_arrows.fram b/test/ok/ok0014_arrows.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0015_ctor.fram b/test/ok/ok0015_ctor.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0016_trivialMatch.fram b/test/ok/ok0016_trivialMatch.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0017_wildcard.fram b/test/ok/ok0017_wildcard.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0018_namePattern.fram b/test/ok/ok0018_namePattern.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0019_simplePattern.fram b/test/ok/ok0019_simplePattern.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0020_patternMatch.fram b/test/ok/ok0020_patternMatch.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0021_simpleMatch.fram b/test/ok/ok0021_simpleMatch.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0022_deepMatch.fram b/test/ok/ok0022_deepMatch.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0023_letPattern.fram b/test/ok/ok0023_letPattern.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0024_letFunc.fram b/test/ok/ok0024_letFunc.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0025_letFuncImplicit.fram b/test/ok/ok0025_letFuncImplicit.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0026_funSugar.fram b/test/ok/ok0026_funSugar.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0027_explicitApp.fram b/test/ok/ok0027_explicitApp.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0028_patArg.fram b/test/ok/ok0028_patArg.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0029_handle.fram b/test/ok/ok0029_handle.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0030_bt.fram b/test/ok/ok0030_bt.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0031_explicitArg.fram b/test/ok/ok0031_explicitArg.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0032_dataArg.fram b/test/ok/ok0032_dataArg.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0033_higherKinds.fram b/test/ok/ok0033_higherKinds.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0034_schemes.fram b/test/ok/ok0034_schemes.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0035_schemes.fram b/test/ok/ok0035_schemes.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0036_schemeAnnot.fram b/test/ok/ok0036_schemeAnnot.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0037_checkScheme.fram b/test/ok/ok0037_checkScheme.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0038_explicitArg.fram b/test/ok/ok0038_explicitArg.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0039_polymorphicImplicit.fram b/test/ok/ok0039_polymorphicImplicit.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0040_polymorphicFields.fram b/test/ok/ok0040_polymorphicFields.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0041_existentialTypes.fram b/test/ok/ok0041_existentialTypes.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0042_existentialTypes.fram b/test/ok/ok0042_existentialTypes.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0043_implicitCtorArgs.fram b/test/ok/ok0043_implicitCtorArgs.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0044_implicitCtorArgs.fram b/test/ok/ok0044_implicitCtorArgs.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0045_recursiveData.fram b/test/ok/ok0045_recursiveData.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0046_mutualDataRec.fram b/test/ok/ok0046_mutualDataRec.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0047_namedParam.fram b/test/ok/ok0047_namedParam.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0048_explicitTypeInst.fram b/test/ok/ok0048_explicitTypeInst.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0049_expilicitInstOrder.fram b/test/ok/ok0049_expilicitInstOrder.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0050_typeArgRename.fram b/test/ok/ok0050_typeArgRename.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0051_existentialTypePattern.fram b/test/ok/ok0051_existentialTypePattern.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0052_emptyMatch.fram b/test/ok/ok0052_emptyMatch.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0053_firstClassHandler.fram b/test/ok/ok0053_firstClassHandler.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0054_firstClassHandler.fram b/test/ok/ok0054_firstClassHandler.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0055_complexHandlers.fram b/test/ok/ok0055_complexHandlers.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0056_complexHandlers.fram b/test/ok/ok0056_complexHandlers.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0057_dataArgLabels.fram b/test/ok/ok0057_dataArgLabels.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0058_unitState.fram b/test/ok/ok0058_unitState.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0059_effectArg.fram b/test/ok/ok0059_effectArg.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0060_returnFinally.fram b/test/ok/ok0060_returnFinally.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0061_returnFinallyMatch.fram b/test/ok/ok0061_returnFinallyMatch.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0062_theLabel.fram b/test/ok/ok0062_theLabel.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0064_typeAnnot.fram b/test/ok/ok0064_typeAnnot.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0066_method.fram b/test/ok/ok0066_method.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0067_pureMethod.fram b/test/ok/ok0067_pureMethod.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0068_shadowCtors.fram b/test/ok/ok0068_shadowCtors.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0069_effectCtorArg.fram b/test/ok/ok0069_effectCtorArg.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0070_effectMethodArg.fram b/test/ok/ok0070_effectMethodArg.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0071_numbers.fram b/test/ok/ok0071_numbers.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0072_strings.fram b/test/ok/ok0072_strings.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0073_extern.fram b/test/ok/ok0073_extern.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0074_implicitWithType.fram b/test/ok/ok0074_implicitWithType.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0075_effectsFromImplicits.fram b/test/ok/ok0075_effectsFromImplicits.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0076_ifExpr.fram b/test/ok/ok0076_ifExpr.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0077_effectResume.fram b/test/ok/ok0077_effectResume.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0078_unitMethods.fram b/test/ok/ok0078_unitMethods.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0079_impureMethod.fram b/test/ok/ok0079_impureMethod.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0080_moduleDef.fram b/test/ok/ok0080_moduleDef.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0081_nestedModule.fram b/test/ok/ok0081_nestedModule.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0082_moduleDataDef.fram b/test/ok/ok0082_moduleDataDef.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0083_pubPatternMatch.fram b/test/ok/ok0083_pubPatternMatch.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0084_operators.fram b/test/ok/ok0084_operators.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0085_letChecked.fram b/test/ok/ok0085_letChecked.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0086_optionState.fram b/test/ok/ok0086_optionState.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0087_opratorOverloading.fram b/test/ok/ok0087_opratorOverloading.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0088_abstractData.fram b/test/ok/ok0088_abstractData.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0089_pubPat.fram b/test/ok/ok0089_pubPat.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0090_lists.fram b/test/ok/ok0090_lists.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0091_namedParamMethod.fram b/test/ok/ok0091_namedParamMethod.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0092_multipleNamedMethodParams.fram b/test/ok/ok0092_multipleNamedMethodParams.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0093_specialBinops.fram b/test/ok/ok0093_specialBinops.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0094_unaryIf.fram b/test/ok/ok0094_unaryIf.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0095_wildcardTypeParam.fram b/test/ok/ok0095_wildcardTypeParam.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0096_fixTypeAnnot.fram b/test/ok/ok0096_fixTypeAnnot.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0097_recursion.fram b/test/ok/ok0097_recursion.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0098_mutualRecursion.fram b/test/ok/ok0098_mutualRecursion.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0099_nestedEffArrows.fram b/test/ok/ok0099_nestedEffArrows.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0100_polymorphicRecursion.fram b/test/ok/ok0100_polymorphicRecursion.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0101_implicitParamsRecord.fram b/test/ok/ok0101_implicitParamsRecord.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0102_simpleRecord.fram b/test/ok/ok0102_simpleRecord.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0103_genericRecords.fram b/test/ok/ok0103_genericRecords.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0104_chars.fram b/test/ok/ok0104_chars.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0105_recFunWithNamedParam.fram b/test/ok/ok0105_recFunWithNamedParam.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0106_recursiveMethod.fram b/test/ok/ok0106_recursiveMethod.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0107_polymorphicRecursion.fram b/test/ok/ok0107_polymorphicRecursion.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0108_modulePattern.fram b/test/ok/ok0108_modulePattern.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0109_fieldPattern.fram b/test/ok/ok0109_fieldPattern.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0110_publicModulePattern.fram b/test/ok/ok0110_publicModulePattern.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0111_optionalParams.fram b/test/ok/ok0111_optionalParams.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0112_pureRecord.fram b/test/ok/ok0112_pureRecord.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0113_pureMatchingNonrecUVar.fram b/test/ok/ok0113_pureMatchingNonrecUVar.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0114_pureTail.fram b/test/ok/ok0114_pureTail.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0115_purePatternMatching.fram b/test/ok/ok0115_purePatternMatching.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0116_pureRecordAccessor.fram b/test/ok/ok0116_pureRecordAccessor.fram old mode 100755 new mode 100644 diff --git a/test/ok/ok0117_comments.fram b/test/ok/ok0117_comments.fram old mode 100755 new mode 100644 diff --git a/test/stdlib/stdlib0000_Int64.fram b/test/stdlib/stdlib0000_Int64.fram old mode 100755 new mode 100644 diff --git a/test/stdlib/stdlib0001_Option.fram b/test/stdlib/stdlib0001_Option.fram old mode 100755 new mode 100644 diff --git a/test/stdlib/stdlib0002_Map.fram b/test/stdlib/stdlib0002_Map.fram old mode 100755 new mode 100644 diff --git a/test/stdlib/stdlib0003_Set.fram b/test/stdlib/stdlib0003_Set.fram old mode 100755 new mode 100644 diff --git a/test/stdlib/stdlib0004_Queue.fram b/test/stdlib/stdlib0004_Queue.fram old mode 100755 new mode 100644 diff --git a/test/test_suite b/test/test_suite old mode 100755 new mode 100644 From 394a919ab6af8626954d572ea268b2d111aa4c86 Mon Sep 17 00:00:00 2001 From: Jakub Chomiczewski Date: Fri, 4 Apr 2025 10:52:15 +0200 Subject: [PATCH 24/27] Correction due to change in syntax --- lib/Map.fram | 30 +++++++++---------- lib/Queue.fram | 16 +++++----- lib/Set.fram | 6 ++-- ...tdlib0002_Map.fram => stdlib0003_Map.fram} | 0 ...tdlib0003_Set.fram => stdlib0004_Set.fram} | 0 ...b0004_Queue.fram => stdlib0005_Queue.fram} | 0 6 files changed, 26 insertions(+), 26 deletions(-) rename test/stdlib/{stdlib0002_Map.fram => stdlib0003_Map.fram} (100%) rename test/stdlib/{stdlib0003_Set.fram => stdlib0004_Set.fram} (100%) rename test/stdlib/{stdlib0004_Queue.fram => stdlib0005_Queue.fram} (100%) diff --git a/lib/Map.fram b/lib/Map.fram index 5c08e383..9e26b15d 100644 --- a/lib/Map.fram +++ b/lib/Map.fram @@ -8,7 +8,7 @@ import open RedBlackTree # Signature #} -implicit ~onError +parameter ~onError pub data Map Key = Map of { T @@ -76,7 +76,7 @@ pub data Map Key = Map of { # @return updated tree ##} , method update : {type Val,E} -> T Val -> Key -> - (Option Val ->[|E] Option Val) ->[|E] T Val + (Option Val ->[E] Option Val) ->[E] T Val {## @brief Method to fold left through structure of map # @param Function that receives key, value and accumulator @@ -85,7 +85,7 @@ pub data Map Key = Map of { # and values of map and accumulator ##} , method foldl : {type Val, type A,E} -> T Val -> - (Key -> Val -> A ->[|E] A) -> A ->[|E] A + (Key -> Val -> A ->[E] A) -> A ->[E] A {## @brief Method to fold right through structure of map # @param Function that receives key, value and accumulator @@ -94,7 +94,7 @@ pub data Map Key = Map of { # and values of map and accumulator ##} , method foldr : {type Val, type A,E} -> T Val -> - (Key -> Val -> A ->[|E] A) -> A ->[|E] A + (Key -> Val -> A ->[E] A) -> A ->[E] A {## @brief Method that returns list of pairs (key,value) ##} @@ -111,24 +111,24 @@ pub data Map Key = Map of { {## @brief Method that maps all values using given function ##} , method mapVal : {type Val, type A, E} -> T Val -> - (Val ->[|E] A) ->[|E] T A + (Val ->[E] A) ->[E] T A {## @brief Method that maps all (key,value) in a map to (key, func key) ##} , method mapKey : {type Val, type A,E} -> T Val -> - (Key ->[|E] A) ->[|E] T A + (Key ->[E] A) ->[E] T A {## @brief Method that applies function to every key and value ##} , method iter : {type Val,E} -> T Val -> - (Key -> Val ->[|E] Unit) ->[|E] Unit + (Key -> Val ->[E] Unit) ->[E] Unit {## @brief Method that joins two maps # @param Function that resolves conflicts # if maps have the same key ##} , method union : {type Val,E} -> T Val -> T Val -> - (Key -> Val -> Val ->[|E] Val) ->[|E] T Val + (Key -> Val -> Val ->[E] Val) ->[E] T Val {## @brief Method that splits map into two maps one with # the keys lower then given key, the other with greater. @@ -606,7 +606,7 @@ pub let make {Key} (compare : Key -> Key ->[] Ordered) = Map { , method removeChange = removeChangeT compare , method member = memberT compare , method find = findT compare - , method findErr = findErrT compare + , method findErr = fn {~onError} => findErrT compare , method update = updateT compare , method foldl = mapFoldl , method foldr = mapFoldr @@ -621,15 +621,15 @@ pub let make {Key} (compare : Key -> Key ->[] Ordered) = Map { , method partionLt = partionLtT compare , method partionGt = partionGtT compare , method lowerBound = lowerBoundT - , method lowerBoundErr = lowerBoundTErr + , method lowerBoundErr = fn {~onError} => lowerBoundTErr , method upperBound = upperBoundT - , method upperBoundErr = upperBoundTErr + , method upperBoundErr = fn {~onError} => upperBoundTErr , method lowerBoundGt = lowerBoundGtT compare - , method lowerBoundGtErr = lowerBoundGtTErr compare + , method lowerBoundGtErr = fn {~onError} => lowerBoundGtTErr compare , method lowerBoundGeq = lowerBoundGeqT compare - , method lowerBoundGeqErr = lowerBoundGeqTErr compare + , method lowerBoundGeqErr = fn {~onError} => lowerBoundGeqTErr compare , method upperBoundLt = upperBoundLtT compare - , method upperBoundLtErr = upperBoundLtTErr compare + , method upperBoundLtErr = fn {~onError} => upperBoundLtTErr compare , method upperBoundLeq = upperBoundLeqT compare - , method upperBoundLeqErr = upperBoundLeqTErr compare + , method upperBoundLeqErr = fn {~onError} => upperBoundLeqTErr compare } diff --git a/lib/Queue.fram b/lib/Queue.fram index d8093f2d..441b2919 100644 --- a/lib/Queue.fram +++ b/lib/Queue.fram @@ -162,11 +162,11 @@ let rec toList queue = pub let fromList list = List.foldLeft snoc emptyQueue list -pub method isEmpty = isEmpty self -pub method snoc = snoc self -pub method tail = tail self -pub method push = snoc self -pub method pop = tail self -pub method head = head self -pub method map = mapQueue self -pub method toList = toList self +pub method isEmpty self = isEmpty self +pub method snoc self = snoc self +pub method tail self = tail self +pub method push self = snoc self +pub method pop self = tail self +pub method head self = head self +pub method map self = mapQueue self +pub method toList self = toList self diff --git a/lib/Set.fram b/lib/Set.fram index 9cca9a64..c1c1410f 100644 --- a/lib/Set.fram +++ b/lib/Set.fram @@ -7,7 +7,7 @@ import open RedBlackTree # Signature of Set -implicit ~onError +parameter ~onError data Interval Value = Inclusion of Value | Exclusion of Value @@ -46,14 +46,14 @@ pub data Set Elem = Set of { # @param Accumulator # @return Result of applying function on elements of set and accumulator ##} - , method foldl : {type A,E} -> T -> (Elem -> A ->[|E] A) -> A ->[|E] A + , method foldl : {type A,E} -> T -> (Elem -> A ->[E] A) -> A ->[E] A {## @brief Method to fold right through structure of set # @param Function that receives element and accumulator # @param Accumulator # @return Result of applying function on elements of set and accumulator ##} - , method foldr : {type A,E} -> T -> (Elem -> A ->[|E] A) -> A ->[|E] A + , method foldr : {type A,E} -> T -> (Elem -> A ->[E] A) -> A ->[E] A {## @brief Method to convert set to list of elements ##} diff --git a/test/stdlib/stdlib0002_Map.fram b/test/stdlib/stdlib0003_Map.fram similarity index 100% rename from test/stdlib/stdlib0002_Map.fram rename to test/stdlib/stdlib0003_Map.fram diff --git a/test/stdlib/stdlib0003_Set.fram b/test/stdlib/stdlib0004_Set.fram similarity index 100% rename from test/stdlib/stdlib0003_Set.fram rename to test/stdlib/stdlib0004_Set.fram diff --git a/test/stdlib/stdlib0004_Queue.fram b/test/stdlib/stdlib0005_Queue.fram similarity index 100% rename from test/stdlib/stdlib0004_Queue.fram rename to test/stdlib/stdlib0005_Queue.fram From 5450ed1a03d25282df43a0fcb16dd06c52513eaa Mon Sep 17 00:00:00 2001 From: Jakub Chomiczewski Date: Thu, 3 Jul 2025 22:11:46 +0200 Subject: [PATCH 25/27] Correcting small mistakes and adding some longly requested papers and other things to understand what is going on in RedBlackTree --- lib/Queue.fram | 34 +++------------------------------- lib/RedBlackTree.fram | 10 ++++++++-- 2 files changed, 11 insertions(+), 33 deletions(-) diff --git a/lib/Queue.fram b/lib/Queue.fram index 441b2919..2c80ae40 100644 --- a/lib/Queue.fram +++ b/lib/Queue.fram @@ -46,7 +46,7 @@ let invalidate state = | _ => state end -let exec_twice hmqueue = +let execTwice hmqueue = match hmqueue with | HMQueue lenf f state lenr r => match exec (exec state) with @@ -73,10 +73,10 @@ let add v1 v2 = let check queue = match queue with | HMQueue lenf f state lenr r => - if leq lenr lenf then exec_twice queue + if leq lenr lenf then execTwice queue else ( let newstate = Reversing Zero f [] r [] in - exec_twice (HMQueue (add lenf lenr) f newstate Zero []) + execTwice (HMQueue (add lenf lenr) f newstate Zero []) ) end @@ -108,34 +108,6 @@ let tail queue = check (HMQueue (subOne lenf) xs (invalidate state) lenr r) end -let foldlRotationState f acc state = - match state with - | Idle => acc - | Done list => List.foldLeft f acc list - | Appending _ list1 list2 => - List.foldLeft f - (List.foldLeft f acc list2) - list1 - | Reversing _ list1 list2 list3 list4 => - List.foldLeft f - (List.foldLeft f - (List.foldLeft f - (List.foldLeft f acc list4) - list3) - list2) - list1 - end - -pub let foldlQueue queue f acc = - match queue with - | HMQueue _ list1 state _ list2 => - List.foldLeft f - (foldlRotationState f - (List.foldLeft f acc list1) - state) - list2 - end - let mapRotationState f state = match state with | Idle => Idle diff --git a/lib/RedBlackTree.fram b/lib/RedBlackTree.fram index cceb1fb0..5862b839 100644 --- a/lib/RedBlackTree.fram +++ b/lib/RedBlackTree.fram @@ -2,8 +2,9 @@ # See LICENSE for details. #} -#import open Prelude -#import open Base/Assert +# Due to frequent request for understanding this file please +# see comments at the end of this file + import List data Color = @@ -326,3 +327,8 @@ pub let rec split compareWithPivot tree = (_v, joinVal left value _l, _r) end end + +# Links to papers: +# https://drive.google.com/drive/folders/11a0Q5LxCHAx5OJARUIng6wymAE_YvzHk?usp=sharing +# Similar implementation: +# https://github.com/standardml/cmlib/blob/master/red-black-tree.sml From 2549f931a7279b44b9abd09e9467f2f3ac617948 Mon Sep 17 00:00:00 2001 From: Jakub Chomiczewski Date: Thu, 23 Oct 2025 08:35:00 +0200 Subject: [PATCH 26/27] Changing to incremental changes - for now queues + red-black tree --- lib/Map.fram | 635 -------------------------------- lib/RedBlackTree.fram | 9 +- lib/Set.fram | 508 ------------------------- test/stdlib/stdlib0003_Map.fram | 87 ----- test/stdlib/stdlib0004_Set.fram | 71 ---- 5 files changed, 7 insertions(+), 1303 deletions(-) delete mode 100644 lib/Map.fram delete mode 100644 lib/Set.fram delete mode 100644 test/stdlib/stdlib0003_Map.fram delete mode 100644 test/stdlib/stdlib0004_Set.fram diff --git a/lib/Map.fram b/lib/Map.fram deleted file mode 100644 index 9e26b15d..00000000 --- a/lib/Map.fram +++ /dev/null @@ -1,635 +0,0 @@ -{# This file is part of DBL, released under MIT license. - # See LICENSE for details. - #} - -import open RedBlackTree - -{# - # Signature - #} - -parameter ~onError - -pub data Map Key = Map of { - T - - {## @brief Creates empty map - ##} - , empty : {type Val} -> T Val - - {## @brief Method to testing whether given map is empty or not - # @return True if it's empty false otherwise - ##} - , method isEmpty : {type Val} -> T Val ->[] Bool - - {## @brief Method for inserting element to the map - # @param Key which will be inserted to the map - # @param Value which will be inserted to the map - # @return Map with inserted value - ##} - , method insert : {type Val} -> T Val -> - Key -> Val ->[] T Val - - {## @brief Method for inserting element to the map - # @param Key which will be inserted to the map - # @param Value which will be inserted to the map - # @return Map with inserted value - # and boolean value if the value was changed - # if the key already existed in map - ##} - , method insertChange : {type Val} -> T Val -> - Key -> Val ->[] (Pair (T Val) Bool) - - {## @brief Method for removing key from the map - # @param Key which will be removed to the map - # @return Map with removed key - ##} - , method remove : {type Val} -> T Val -> Key ->[] T Val - - {## @brief Method for removing key from the map - # @param Key which will be removed to the map - # @return Map with removed key - # and boolean value if the map was changed - ##} - , method removeChange : {type Val} -> T Val -> - Key ->[] (Pair (T Val) Bool) - - {## @brief Method for checking if a given key is present in a map - ##} - , method member : {type Val} -> T Val -> Key ->[] Bool - - {## @brief Method for getting value mapping from a key - # returns None if key is not found - ##} - , method find : {type Val} -> T Val -> Key ->[] Option Val - - {## @brief Method for getting value mapping from a key, - # calls `~onError` if key is not found - ##} - , method findErr : - {type Val, Err, ~onError : Unit ->[Err] Val} -> T Val -> Key ->[Err] Val - - {## @brief Method to update mapping on a key using a function - # @param key - # @param f is called with Option Val based on if the key has mapping - # in the input tree and should return Option Val to update the tree - # @return updated tree - ##} - , method update : {type Val,E} -> T Val -> Key -> - (Option Val ->[E] Option Val) ->[E] T Val - - {## @brief Method to fold left through structure of map - # @param Function that receives key, value and accumulator - # @param Accumulator - # @return Result of applying function on keys - # and values of map and accumulator - ##} - , method foldl : {type Val, type A,E} -> T Val -> - (Key -> Val -> A ->[E] A) -> A ->[E] A - - {## @brief Method to fold right through structure of map - # @param Function that receives key, value and accumulator - # @param Accumulator - # @return Result of applying function on keys - # and values of map and accumulator - ##} - , method foldr : {type Val, type A,E} -> T Val -> - (Key -> Val -> A ->[E] A) -> A ->[E] A - - {## @brief Method that returns list of pairs (key,value) - ##} - , method toList : {type Val} -> T Val ->[] List (Pair Key Val) - - {## @brief Method that returns list of values - ##} - , method toValueList : {type Val} -> T Val ->[] List Val - - {## @brief Method that returns list of keys - ##} - , method domain : {type Val} -> T Val ->[] List Key - - {## @brief Method that maps all values using given function - ##} - , method mapVal : {type Val, type A, E} -> T Val -> - (Val ->[E] A) ->[E] T A - - {## @brief Method that maps all (key,value) in a map to (key, func key) - ##} - , method mapKey : {type Val, type A,E} -> T Val -> - (Key ->[E] A) ->[E] T A - - {## @brief Method that applies function to every key and value - ##} - , method iter : {type Val,E} -> T Val -> - (Key -> Val ->[E] Unit) ->[E] Unit - - {## @brief Method that joins two maps - # @param Function that resolves conflicts - # if maps have the same key - ##} - , method union : {type Val,E} -> T Val -> T Val -> - (Key -> Val -> Val ->[E] Val) ->[E] T Val - - {## @brief Method that splits map into two maps one with - # the keys lower then given key, the other with greater. - # @return map with lower keys, Some value if key was present, - # map with greater keys - ##} - , method partion : {type Val} -> T Val -> Key ->[] - (Pair (Pair (T Val) (Option Val)) (T Val)) - - {## @brief Method that splits map into two maps one with - # the keys lower then given key, the other with greater or equal. - ##} - , method partionLt : {type Val} -> T Val -> Key ->[] Pair (T Val) (T Val) - - {## @brief Method that splits map into two maps one with - # the keys lower or equal then given key, the other with greater. - ##} - , method partionGt : {type Val} -> T Val -> Key ->[] Pair (T Val) (T Val) - - {## @brief Method that returns lowest pair (key,value) in a map - # @return Some (key,value) if the smallest key exist or otherwise None - ##} - , method lowerBound : {type Val} -> T Val ->[] Option (Pair Key Val) - - {## @brief Method that returns lowest pair (key,value) in a map - # @return (key,value) or error - ##} - , method lowerBoundErr : - {type Val, Err, ~onError : Unit ->[Err] (Pair Key Val)} -> - T Val ->[Err] (Pair Key Val) - - {## @brief Method that returns greatest pair (key,value) in a map - # @return Some (key,value) if the greatest key exist or otherwise None - ##} - , method upperBound : {type Val} -> T Val ->[] Option (Pair Key Val) - - {## @brief Method that returns greatest pair (key,value) in a map - # @return (key,value) or error - ##} - , method upperBoundErr : - {type Val, Err, ~onError : Unit ->[Err] (Pair Key Val)} -> - T Val ->[Err] (Pair Key Val) - - {## @brief Method that returns the lowest (key,value) greater than given key - # @return Some (key,value) or None - ##} - , method lowerBoundGt : {type Val} -> T Val -> Key ->[] - Option (Pair Key Val) - - {## @brief Method that returns the lowest (key,value) greater than given key - # @return (key,value) or error - ##} - , method lowerBoundGtErr : - {type Val, Err, ~onError : Unit ->[Err] (Pair Key Val)} -> - T Val -> Key ->[Err] (Pair Key Val) - - {## @brief Method that returns the lowest (key,value) greater - # or equal than given key - # @return Some (key,value) or None - ##} - , method lowerBoundGeq : {type Val} -> T Val -> Key ->[] - Option (Pair Key Val) - - {## @brief Method that returns the lowest (key,value) greater - # or equal than given key - # @return (key,value) or error - ##} - , method lowerBoundGeqErr : - {type Val, Err, ~onError : Unit ->[Err] (Pair Key Val)} -> - T Val -> Key ->[Err] (Pair Key Val) - - {## @brief Method that returns the greatest (key,value) lower than given key - # @return Some (key,value) or None - ##} - , method upperBoundLt : {type Val} -> T Val -> - Key ->[] Option (Pair Key Val) - - {## @brief Method that returns the greatest (key,value) lower than given key - # @return (key,value) or error - ##} - , method upperBoundLtErr : - {type Val, Err, ~onError : Unit ->[Err] (Pair Key Val)} -> - T Val -> Key ->[Err] (Pair Key Val) - - {## @brief Method that returns the greatest (key,value) lower - # or equal than given key - # @return Some (key,value) or None - ##} - , method upperBoundLeq : {type Val,E} -> T Val -> - Key ->[] Option (Pair Key Val) - - {## @brief Method that returns the greatest (key,value) lower - # or equal than given key - # @return (key,value) or error - ##} - , method upperBoundLeqErr : - {type Val, Err, ~onError : Unit ->[Err] (Pair Key Val)} -> - T Val -> Key ->[Err] (Pair Key Val) -} - -# implementation - -let keyComp compare key (key', _) = compare key key' - -let isEmpty tree = - match tree with - | Leaf => True - | _ => False - end - -let insert compare tree key val = - match search (keyComp compare key) tree [] with - | (Leaf, zipper) => zipRed (key,val) Leaf Leaf zipper - | ((Node {color, size, left, right}), zipper) => - zip (construct color size left (key,val) right) zipper - end - -let insert' compare tree key val = - match search (keyComp compare key) tree [] with - | (Leaf, zipper) => (zipRed (key,val) Leaf Leaf zipper, False) - | (Node {color, size, left, right}, zipper) => - (zip (construct color size left (key,val) right) zipper, True) - end - -let remove compare tree key = - match search (keyComp compare key) tree [] with - | (Leaf,_) => tree - | (Node {color, left, right}, zipper) => - delete color left right zipper - end - -let remove' compare tree key = - match search (keyComp compare key) tree [] with - | (Leaf,_) => (tree,False) - | (Node {color, left, right}, zipper) => - (delete color left right zipper, True) - end - -let rec member compare tree key = - match tree with - | Leaf => False - | Node {left, value = (key',_), right} => - match compare key key' with - | Lt => member compare left key - | Eq => True - | Gt => member compare right key - end - end - -let rec find compare tree key = - match tree with - | Leaf => None - | Node {left, value = (key', val), right} => - match compare key key' with - | Lt => find compare left key - | Eq => Some val - | Gt => find compare right key - end - end - -let rec findErr compare tree key = - match tree with - | Leaf => ~onError () - | Node {left, value = (key', val), right} => - match compare key key' with - | Lt => findErr compare left key - | Eq => val - | Gt => findErr compare right key - end - end - -let update compare tree key f = - match search (keyComp compare key) tree [] with - | (Leaf, zipper) => - match f None with - | None => tree - | Some x => zipRed (key,x) Leaf Leaf zipper - end - | (Node {color, size, left, value = (_, val), right}, zipper) => - match f (Some val) with - | None => delete color left right zipper - | Some x => zip (construct color size left (key,x) right) zipper - end - end - -let rec foldr func tree acc = - match tree with - | Leaf => acc - | Node {left, value = (key, val), right} => - let val_right = foldr func right acc - let val_middle = func key val val_right in - foldr func left val_middle - end - -let rec foldl func tree acc = - match tree with - | Leaf => acc - | Node {left, value = (key, val), right} => - let val_left = foldl func left acc - let val_middle = func key val val_left in - foldl func right val_middle - end - -let rec map tree func = - match tree with - | Leaf => Leaf - | Node {color, size, left, value = (key,value), right} => - let left' = map left func - let right' = map right func in - construct color size left' (key,func value) right' - end - -let rec map2 tree func = - match tree with - | Leaf => Leaf - | Node {color, size, left, value = (key, _), right} => - let left' = map2 left func - let right' = map2 right func in - construct color size left' (key, func key) right' - end - -let rec iter tree func = - match tree with - | Leaf => () - | Node {left, value = (key,value), right} => - iter left func; - func key value; - iter right func - end - -let rec union compare tree1 tree2 merge = - match tree1 with - | Leaf => tree2 - | Node {left = left1, value = (key1,value1), right = right1} => - match tree2 with - | Leaf => tree1 - | _ => - let (output,left2,right2) = split (keyComp compare key1) tree2 - let new_pair = - match output with - | None => (key1,value1) - | Some (_,value2) => (key1, merge key1 value1 value2) - end - let left' = union compare left1 left2 merge - let right' = union compare right1 right2 merge in - joinVal left' new_pair right' - end - end - -let partionLt compare tree key = - let comparator (key2, _) = - match compare key key2 with - | Lt => Lt - | _ => Gt - end - let (_,left,right) = split comparator tree in - (left, right) - -let partionGt compare tree key = - let comparator (key2, _) = - match compare key key2 with - | Gt => Gt - | _ => Lt - end - let (_,left,right) = split comparator tree in - (left, right) - -let rec lowerBound tree = - match tree with - | Leaf => None - | Node {left = Leaf, value} => Some value - | Node {left} => lowerBound left - end - -let lowerBoundErr tree = - match lowerBound tree with - | None => ~onError () - | Some x => x - end - -let rec upperBound tree = - match tree with - | Leaf => None - | Node {value, right=Leaf} => Some value - | Node {right} => upperBound right - end - -let upperBoundErr tree = - match upperBound tree with - | None => ~onError () - | Some x => x - end - -let rec lowerBoundGt compare tree key = - match tree with - | Leaf => None - | Node {left, value = (key1, value), right} => - match compare key key1 with - | Lt => - match lowerBoundGt compare left key with - | None => Some (key1, value) - | x => x - end - | Eq => lowerBound right - | Gt => lowerBoundGt compare right key - end - end - -let lowerBoundGtErr compare tree key = - match lowerBoundGt compare tree key with - | None => ~onError () - | Some x => x - end - -let rec lowerBoundGeq compare tree key = - match tree with - | Leaf => None - | Node {left, value = (key1, value), right} => - match compare key key1 with - | Lt => - match lowerBoundGeq compare left key with - | None => Some (key1,value) - | x => x - end - | Eq => Some (key1, value) - | Gt => lowerBoundGeq compare right key - end - end - -let lowerBoundGeqErr compare tree key = - match lowerBoundGeq compare tree key with - | None => ~onError () - | Some x => x - end - -let rec upperBoundLt compare tree key = - match tree with - | Leaf => None - | Node {left, value = (key1,value), right} => - match compare key key1 with - | Lt => upperBoundLt compare left key - | Eq => upperBound left - | Gt => - match upperBoundLt compare right key with - | None => Some (key1,value) - | x => x - end - end - end - -let upperBoundLtErr compare tree key = - match upperBoundLt compare tree key with - | None => ~onError () - | Some x => x - end - -let rec upperBoundLeq compare tree key = - match tree with - | Leaf => None - | Node {left, value = (key1,value), right} => - match compare key key1 with - | Lt => upperBoundLt compare left key - | Eq => Some (key1,value) - | Gt => - match upperBoundLeq compare right key with - | None => Some (key1,value) - | x => x - end - end - end - -let upperBoundLeqErr compare tree key = - match upperBoundLeq compare tree key with - | None => ~onError () - | Some x => x - end - -let toList tree = foldr (fn key value acc => (key, value) :: acc) tree [] - -let toValueList tree = foldr (fn key value acc => value :: acc) tree [] - -let domain tree = foldr (fn key value acc => key :: acc) tree [] - -let partion compare tree key = - let (output,left,right) = split (keyComp compare key) tree in - match output with - | None => (left,None,right) - | Some (_,x) => (left,Some x, right) - end - -data MapT Key Val = MapT of Tree (Pair Key Val) - -# Wrappers -let isEmptyT (MapT tree) = isEmpty tree - -let insertT compare (MapT tree) key val = MapT (insert compare tree key val) - -let insertChangeT compare (MapT tree) key val = - let (tree,bool) = insert' compare tree key val in (MapT tree, bool) - -let removeT compare (MapT tree) key = MapT (remove compare tree key) - -let removeChangeT compare (MapT tree) key = - let (tree,bool) = remove' compare tree key in (MapT tree, bool) - -let memberT compare (MapT tree) key = member compare tree key - -let findT compare (MapT tree) key = find compare tree key - -let findErrT compare (MapT tree) key = findErr compare tree key - -let updateT compare (MapT tree) key f = MapT (update compare tree key f) - -let mapFoldl (MapT tree) func acc = foldl func tree acc - -let mapFoldr (MapT tree) func acc = foldr func tree acc - -let toListT (MapT tree) = toList tree - -let toValueListT (MapT tree) = toValueList tree - -let domainT (MapT tree) = domain tree - -let mapVal (MapT tree) func = MapT (map tree func) - -let mapKey (MapT tree) func = MapT (map2 tree func) - -let iterT (MapT tree) func = iter tree func - -let unionT compare (MapT tree1) (MapT tree2) merge = - MapT (union compare tree1 tree2 merge) - -let partionT compare (MapT tree) key = - let (t1,v,t2) = partion compare tree key in (MapT t1, v, MapT t2) - -let partionLtT compare (MapT tree) key = - let (t1,t2) = partionLt compare tree key in (MapT t1, MapT t2) - -let partionGtT compare (MapT tree) key = - let (t1,t2) = partionGt compare tree key in (MapT t1, MapT t2) - -let lowerBoundT (MapT tree) = lowerBound tree - -let lowerBoundTErr (MapT tree) = lowerBoundErr tree - -let upperBoundT (MapT tree) = upperBound tree - -let upperBoundTErr (MapT tree) = upperBoundErr tree - -let lowerBoundGtT compare (MapT tree) key = lowerBoundGt compare tree key - -let lowerBoundGtTErr compare (MapT tree) key = lowerBoundGtErr compare tree key - -let upperBoundLtT compare (MapT tree) key = upperBoundLt compare tree key - -let upperBoundLtTErr compare (MapT tree) key = upperBoundLtErr compare tree key - -let lowerBoundGeqT compare (MapT tree) key = lowerBoundGeq compare tree key - -let lowerBoundGeqTErr compare (MapT tree) key = - lowerBoundGeqErr compare tree key - -let upperBoundLeqT compare (MapT tree) key = upperBoundLeq compare tree key - -let upperBoundLeqTErr compare (MapT tree) key = - upperBoundLeqErr compare tree key - -pub let make {Key} (compare : Key -> Key ->[] Ordered) = Map { - T = MapT Key - , empty = MapT Leaf - , method isEmpty = isEmptyT - , method insert = insertT compare - , method insertChange = insertChangeT compare - , method remove = removeT compare - , method removeChange = removeChangeT compare - , method member = memberT compare - , method find = findT compare - , method findErr = fn {~onError} => findErrT compare - , method update = updateT compare - , method foldl = mapFoldl - , method foldr = mapFoldr - , method toList = toListT - , method toValueList = toValueListT - , method domain = domainT - , method mapVal = mapVal - , method mapKey = mapKey - , method iter = iterT - , method union = unionT compare - , method partion = partionT compare - , method partionLt = partionLtT compare - , method partionGt = partionGtT compare - , method lowerBound = lowerBoundT - , method lowerBoundErr = fn {~onError} => lowerBoundTErr - , method upperBound = upperBoundT - , method upperBoundErr = fn {~onError} => upperBoundTErr - , method lowerBoundGt = lowerBoundGtT compare - , method lowerBoundGtErr = fn {~onError} => lowerBoundGtTErr compare - , method lowerBoundGeq = lowerBoundGeqT compare - , method lowerBoundGeqErr = fn {~onError} => lowerBoundGeqTErr compare - , method upperBoundLt = upperBoundLtT compare - , method upperBoundLtErr = fn {~onError} => upperBoundLtTErr compare - , method upperBoundLeq = upperBoundLeqT compare - , method upperBoundLeqErr = fn {~onError} => upperBoundLeqTErr compare -} diff --git a/lib/RedBlackTree.fram b/lib/RedBlackTree.fram index 5862b839..cd3cf0e3 100644 --- a/lib/RedBlackTree.fram +++ b/lib/RedBlackTree.fram @@ -328,7 +328,12 @@ pub let rec split compareWithPivot tree = end end -# Links to papers: -# https://drive.google.com/drive/folders/11a0Q5LxCHAx5OJARUIng6wymAE_YvzHk?usp=sharing +# Papers to read: +# A dichromatic framework for balanced trees. Leo J. Guibas; Robert Sedgewick +# DOI: 10.1109/SFCS.1978.3 +# Efficient implementation of red-black trees with split and catenate operations. +# Ron Wein +# Updating a balanced search tree in O(1) rotations. Robert Tarjan +# DOI: 10.1016/0020-0190(83)90099-6 # Similar implementation: # https://github.com/standardml/cmlib/blob/master/red-black-tree.sml diff --git a/lib/Set.fram b/lib/Set.fram deleted file mode 100644 index c1c1410f..00000000 --- a/lib/Set.fram +++ /dev/null @@ -1,508 +0,0 @@ -{# This file is part of DBL, released under MIT license. - # See LICENSE for details. - #} - - -import open RedBlackTree - -# Signature of Set - -parameter ~onError - -data Interval Value = Inclusion of Value | Exclusion of Value - -pub data Set Elem = Set of { - T - - {## @brief Creates empty set - ##} - , empty : T - - {## @brief Method to testing whether given set is empty or not - # @return True if it's empty False otherwise - ##} - , method isEmpty : T ->[] Bool - - {## @brief Method for inserting element to the set - # @param Element which will be inserted to the set - # @return Set with inserted value - ##} - , method insert : T -> Elem ->[] T - - {## @brief Method for removing element from the set - # @param Element which will be removed - # @return Set with removed element - ##} - , method remove : T -> Elem ->[] T - - {## @brief Method to test whether given element is in a given set or not - # @param Element which will be searched - # @return True if given element is in given set, false otherwise - ##} - , method member : T -> Elem ->[] Bool - - {## @brief Method to fold left through structure of set - # @param Function that receives element and accumulator - # @param Accumulator - # @return Result of applying function on elements of set and accumulator - ##} - , method foldl : {type A,E} -> T -> (Elem -> A ->[E] A) -> A ->[E] A - - {## @brief Method to fold right through structure of set - # @param Function that receives element and accumulator - # @param Accumulator - # @return Result of applying function on elements of set and accumulator - ##} - , method foldr : {type A,E} -> T -> (Elem -> A ->[E] A) -> A ->[E] A - - {## @brief Method to convert set to list of elements - ##} - , method toList : T ->[] List Elem - - {## @brief Method to create union of two sets - # @param Set - # @return Union of two sets - ##} - , method union : T -> T ->[] T - - {## @brief Method to create intersection of two sets - # @param Set - # @return Intersection of two sets - ##} - , method intersection : T -> T ->[] T - - {## @brief Method to create difference of two sets - # @param Set - # @return Difference of two sets - ##} - , method difference : T -> T ->[] T - - {## @brief Method to check if two sets are equal - # @param Set - # @return True if two sets are equal, false otherwise. - ##} - , method eq : T -> T ->[] Bool - - {## @brief Method to check if set which called this method is - # subset of a given set - # @param Set - # @return True if set is subset, false otherwise. - ##} - , method subset : T -> T ->[] Bool - - {## @brief Split set to two sets one containing elements - # lesser then given element, second one containing equal or greater - # @param Elem - # @return Pair of sets with order and specification previously mentioned - ##} - , method partionLt : T -> Elem ->[] (Pair T T) - - {## @brief Split set to two sets one containing elements - # lesser or equal then given element, second one containing greater - # @param Elem - # @return Pair of sets with order and specification previously mentioned - ##} - , method partionGt : T -> Elem ->[] (Pair T T) - - {## @brief Method that returns lowest stored value in a set - # @return Some value if the smallest element exist or otherwise None - ##} - , method lowerBound : T ->[] Option Elem - - {## @brief Method that returns lowest stored value in a set - # @return smallest element or error - ##} - , method lowerBoundErr : - {Err, ~onError : Unit ->[Err] Elem} -> T ->[Err] Elem - - {## @brief Method that returns the greatest stored value in a set - # @return Some value if the greatest element exist or otherwise None - ##} - , method upperBound : T ->[] Option Elem - - {## @brief Method that returns the greatest stored value in a set - # @return greatest element or error - ##} - , method upperBoundErr : - {Err, ~onError : Unit ->[Err] Elem} -> T ->[Err] Elem - - {## @brief Method that returns the lowest element greater than given element - # @return Some value or None - ##} - , method lowerBoundGt : T -> Elem ->[] Option Elem - - {## @brief Method that returns the lowest element greater than given element - # @return value or error - ##} - , method lowerBoundGtErr : - {Err, ~onError : Unit ->[Err] Elem} -> T -> Elem ->[Err] Elem - - {## @brief Method that returns the lowest element greater - # or equal than given element - # @return Some value or None - ##} - , method lowerBoundGeq : T -> Elem ->[] Option Elem - - {## @brief Method that returns the lowest element greater - # or equal than given element - # @return value or error - ##} - , method lowerBoundGeqErr : - {Err, ~onError : Unit ->[Err] Elem} -> T -> Elem ->[Err] Elem - - {## @brief Method that returns the greatest element lower than given element - # @return Some value or None - ##} - , method upperBoundLt : T -> Elem ->[] Option Elem - - {## @brief Method that returns the greatest element lower than given element - # @return value or error - ##} - , method upperBoundLtErr : - {Err, ~onError : Unit ->[Err] Elem} -> T -> Elem ->[Err] Elem - - {## @brief Method that returns the greatest element lower - # or equal than given element - # @return Some value or None - ##} - , method upperBoundLeq : T -> Elem ->[] Option Elem - - {## @brief Method that returns the greatest element lower - # or equal than given element - # @return value or error - ##} - , method upperBoundLeqErr : - {Err, ~onError : Unit ->[Err] Elem} -> T -> Elem ->[Err] Elem -} - -# Red black tree implementation - -data rec Q Val = Nil | E of Val, Q Val | T of Tree Val, Q Val - -let rec eqMain compare qs1 qs2 = - match (qs1,qs2) with - | (Nil,Nil) => True - - | (Nil, E _ _) => False - - | (E _ _, Nil) => False - - | (T Leaf rest, _) => eqMain compare rest qs2 - - | (_, T Leaf rest) => eqMain compare qs1 rest - - | (T (Node {left, value = elem, right}) rest, _) => - eqMain compare (T left (E elem (T right rest))) qs2 - - | (_, T (Node {left, value = elem, right}) rest) => - eqMain compare qs1 (T left (E elem (T right rest))) - - | (E elem1 rest1, E elem2 rest2) => - match compare elem1 elem2 with - | Eq => eqMain compare rest1 rest2 - | _ => False - end - end - -let rec subsetMain comp qs1 qs2 = - match (qs1,qs2) with - | (Nil,_) => True - - | (E _ _ , Nil) => False - - | (T Leaf rest, _) => subsetMain comp rest qs2 - - | (_ , T Leaf rest) => subsetMain comp qs1 rest - - | (T (Node {left, value = elem, right}) rest, _) => - subsetMain comp (T left (E elem (T right rest))) qs2 - - | (_, T (Node {left, value = elem, right}) rest) => - subsetMain comp qs1 (T left (E elem (T right rest))) - - | (E elem1 rest1, E elem2 rest2) => - match comp elem1 elem2 with - | Lt => False - | Eq => subsetMain comp rest1 rest2 - | Gt => subsetMain comp qs1 rest2 - end - end - -let partionLt compare tree key1 = - let comparator key2 = - match compare key1 key2 with - | Gt => Gt - | _ => Lt - end - let (_,left,right) = split comparator tree in - (left,right) - -let partionGt compare tree key1 = - let comparator key2 = - match compare key1 key2 with - | Lt => Lt - | _ => Gt - end - let (_, left,right) = split comparator tree in - (left,right) - -let rec least tree = - match tree with - | Leaf => None - | Node {left = Leaf, value} => Some value - | Node {left} => least left - end - -let leastErr tree = - match least tree with - | None => ~onError () - | Some x => x - end - -let rec greatest tree = - match tree with - | Leaf => None - | Node {value, right = Leaf} => Some value - | Node {right} => greatest right - end - -let greatestErr tree = - match greatest tree with - | None => ~onError () - | Some x => x - end - -let empty = Leaf - -let isEmpty tree = - match tree with - | Leaf => True - | _ => False - end - -let rec member compare tree elem = - match tree with - | Leaf => False - | Node {left, value, right} => - match compare elem value with - | Lt => member compare left elem - | Gt => member compare right elem - | Eq => True - end - end - -let insert compare tree elem = - match search (compare elem) tree [] with - | (Leaf,zipper) => zipRed elem Leaf Leaf zipper - | (Node ,_) => tree - end - -let remove compare tree elem = - match search (compare elem) tree [] with - | (Leaf, _) => tree - | (Node {color, left, right}, zipper) => delete color left right zipper - end - -let rec _search compare tree elem = - match tree with - | Leaf => False - | Node {left, value, right} => - match compare elem value with - | Lt => _search compare left elem - | Gt => _search compare right elem - | Eq => True - end - end - -let rec setFoldl tree func acc = - match tree with - | Leaf => acc - | Node {left, value, right} => - setFoldl right func (func value (setFoldl left func acc)) - end - -let rec setFoldr tree func acc = - match tree with - | Leaf => acc - | Node {left, value, right} => - setFoldr left func (func value (setFoldr right func acc)) - end - -let rec toList acc tree = - match tree with - | Leaf => acc - | Node {left, value, right} => - toList (value :: toList acc right) left - end - -let rec union compare tree1 tree2 = - match tree1 with - | Leaf => tree2 - | Node {left = left1, value = key1, right = right1} => - match tree2 with - | Leaf => tree1 - | Node => - let (_,left2,right2) = split (compare key1) tree2 in - let left' = union compare left1 left2 - let right' = union compare right1 right2 in - joinVal left' key1 right' - end - end - -let rec intersection compare tree1 tree2 = - match tree1 with - | Leaf => Leaf - | Node {left = left1, value = key1, right = right1} => - match tree2 with - | Leaf => Leaf - | _ => - let (value_out, left2, right2) = split (compare key1) tree2 - let left = intersection compare left1 left2 - let right = intersection compare right1 right2 - in - match value_out with - | Some _ => joinVal left key1 right - | None => join left right - end - end - end - -let rec difference compare tree1 tree2 = - match tree1 with - | Leaf => Leaf - - | Node {left = left1, value = key1, right = right1} => - match tree2 with - | Leaf => tree1 - | _ => - let (value_out, left2, right2) = split (compare key1) tree2 - let left = difference compare left1 left2 - let right = difference compare right1 right2 - in - match value_out with - | Some _ => join left right - | None => joinVal left key1 right - end - end - end - -let eq compare set1 set2 = eqMain compare (T set1 Nil) (T set2 Nil) - -let subset compare set1 set2 = subsetMain compare (T set1 Nil) (T set2 Nil) - -let rec leastGt compare tree val = - match tree with - | Leaf => None - | Node {left, value = key, right} => - match compare val key with - | Lt => - let x = leastGt compare left val in - match x with - | None => Some key - | _ => x - end - | Eq => least right - | Gt => leastGt compare right val - end - end - -let leastGtErr compare tree val = - match leastGt compare tree val with - | None => ~onError () - | Some x => x - end - -let rec leastGeq compare tree val = - match tree with - | Leaf => None - | Node {left, value = key, right} => - match compare val key with - | Lt => - match leastGeq compare left val with - | None => Some key - | x => x - end - | Eq => Some val - | Gt => leastGeq compare right val - end - end - -let leastGeqErr compare tree val = - match leastGeq compare tree val with - | None => ~onError () - | Some x => x - end - -let rec greatestLt compare tree val = - match tree with - | Leaf => None - | Node {left, value = key, right} => - match compare val key with - | Lt => greatestLt compare left val - | Eq => greatest left - | Gt => - match greatestLt compare right val with - | None => Some key - | x => x - end - end - end - -let greatestLtErr compare tree val = - match greatestLt compare tree val with - | None => ~onError () - | Some x => x - end - -let rec greatestLeq compare tree val = - match tree with - | Leaf => None - | Node {left, value = key, right} => - match compare val key with - | Lt => greatestLeq compare left val - | Eq => Some val - | Gt => - match greatestLeq compare right val with - | None => Some key - | x => x - end - end - end - -let greatestLeqErr compare tree val = - match greatestLeq compare tree val with - | None => ~onError () - | Some x => x - end - - -pub let make {Val} (compare : Val -> Val ->[] Ordered) = Set { - T = Tree Val - , empty = empty - , method isEmpty = isEmpty - , method insert = insert compare - , method remove = remove compare - , method member = member compare - , method foldl = setFoldl - , method foldr = setFoldr - , method toList = toList [] - , method union = union compare - , method intersection = intersection compare - , method difference = difference compare - , method eq = eq compare - , method subset = subset compare - , method partionLt = partionLt compare - , method partionGt = partionGt compare - , method lowerBound = least - , method lowerBoundErr = leastErr - , method upperBound = greatest - , method upperBoundErr = greatestErr - , method lowerBoundGt = leastGt compare - , method lowerBoundGtErr = leastGtErr compare - , method lowerBoundGeq = leastGeq compare - , method lowerBoundGeqErr = leastGeqErr compare - , method upperBoundLt = greatestLt compare - , method upperBoundLtErr = greatestLtErr compare - , method upperBoundLeq = greatestLeq compare - , method upperBoundLeqErr = greatestLeqErr compare -} diff --git a/test/stdlib/stdlib0003_Map.fram b/test/stdlib/stdlib0003_Map.fram deleted file mode 100644 index a3a9437b..00000000 --- a/test/stdlib/stdlib0003_Map.fram +++ /dev/null @@ -1,87 +0,0 @@ -import Map -import open List - -let lt (v1 : Int) (v2 : Int) = - if v1 < v2 then Lt - else if v2 < v1 then Gt - else Eq - -let Map.Map {module IntMap} = Map.make lt - -let x = IntMap.empty - -# insert check -let y = x.insert 1 1 -let z = x.insert 1 "a" - -# isEmpty check -let _ = assert {msg="Failed isEmpty"} (y.isEmpty == False) -let _ = assert {msg="Failed isEmpty"} (z.isEmpty == False) -let _ = assert {msg="Failed isEmpty"} (y.remove 1 >. isEmpty) - -# domain check -let z = y.insert 2 1 >. insert 3 2 >. insert 4 3 -let _ = assert {msg="Failed domain"} - (z.domain == [1,2,3,4] && z.toValueList == [1,1,2,3]) - -# toList check -let _ = assert {msg="Failed toList"} ((z.toList.foldLeft - (fn acc (key,val) => val :: acc) []) == [1,1,2,3].rev) - -# foldl check -let _ = assert {msg="Failed foldl"} - (z.foldl (fn key val acc => key :: acc) [] == [1,2,3,4].rev) - - -# member check -let _ = assert {msg="Failed member"} (z.member 1) - -# find check -let _ = assert {msg="Failed find"} - (match z.find 1 with | None => False | _ => True end) - -# update change check -let _ = assert {msg="Failed update"} - (let f a = - match a with - | None => Some 2 - | Some _ => Some 0 - end in - z.update 1 f - >. toValueList == [0,1,2,3]) - -# update add check -let _ = assert {msg="Failed update"} - (let f a = - match a with - | None => Some 2 - | Some _ => Some 0 - end in - z.update 0 f - >. toValueList == [2,1,1,2,3]) - -# map check -let _ = assert {msg="Failed map"} - (z.mapVal (fn x => if x == x.shiftr 1 >. shiftl 1 then -x else x) - >. toValueList == [1,1,(0-2),3]) - -# union check -let y = x.insert 1.neg 2 >. insert 2.neg 3 >. insert 0 1 >. insert 1 10 -let w = z.union y (fn key val1 val2 => val2) -let _ = assert {msg="Failed union"} (w.toValueList == [3,2,1,10,1,2,3]) - -# partion check -let q = w.partion 0 -let _ = assert {msg="Failed partion"} (fst (fst q) >. toValueList == [3,2]) -let _ = assert {msg="Failed partion"} (snd q >. toValueList == [10,1,2,3]) - -# partionLt check -let q = w.partionLt 0 -let _ = assert {msg="Failed partionLt"} (fst q >. toValueList == [3,2,1]) -let _ = assert {msg="Failed partionLt"} (snd q >. toValueList == [10,1,2,3]) - -# partionGt check -let q = w.partionGt 0 -let _ = assert {msg="Failed partionGt"} (fst q >. toValueList == [3,2]) -let _ = assert {msg="Failed partionGt"} (snd q >. toValueList == [1,10,1,2,3]) - diff --git a/test/stdlib/stdlib0004_Set.fram b/test/stdlib/stdlib0004_Set.fram deleted file mode 100644 index 9f58d451..00000000 --- a/test/stdlib/stdlib0004_Set.fram +++ /dev/null @@ -1,71 +0,0 @@ -import Set -import open List - -let lt (v1 : Int) (v2 : Int) = - if v1 < v2 then Lt - else if v2 < v1 then Gt - else Eq - -let Set.Set {module IntSet} = Set.make lt - -# empty check -let x = IntSet.empty -let _ = assert {msg="Failed empty"} (x.isEmpty) - -let x = x.insert 0 - -# toList check -let _ = assert {msg="Failed toList"} (x.toList == [0]) - -# insert check -let y = x.insert 1 -let _ = assert {msg="Failed insert"} (y.toList == [0,1]) -let _ = assert {msg="Failed insert"} (y.insert 2 >. toList == [0,1,2]) - -# remove check -let y = y.insert 2 >. insert 3 -let _ = assert {msg="Failed remove"} (y.remove 1 >. toList == [0,2,3]) - -# member check -let _ = assert {msg="Failed check"} (y.member 1) -let _ = assert {msg="Failed check"} (not (y.member 10)) - -# foldl/r check -let _ = assert {msg="Failed foldl"} (y.foldl (fn x acc => x + acc) 0 == 6) -let _ = assert {msg="Failed foldr"} (y.foldr (fn x acc => x + acc) 0 == 6) - -# union check -let x = x.insert 4 >. insert 5 >. insert 6 -let _ = assert {msg="Failed union"} (y.union x >. toList == [0,1,2,3,4,5,6]) - -# intersection check -let _ = assert {msg="Failed intersection"} (x.intersection y >. toList == [0]) - -# diffrence check -let _ = assert {msg="Failed difference"} (y.difference x >. toList == [1,2,3]) -let _ = assert {msg="Failed difference"} (x.difference y >. toList == [4,5,6]) - -# eq check -let _ = assert {msg="Failed eq"} (x.eq x) -let _ = assert {msg="Failed eq"} (not (x.eq y)) - -# subset check -let _ = assert {msg="Failed subset"} (IntSet.empty.subset x) -let _ = assert {msg="Failed subset"} - (IntSet.empty.insert 0 >. insert 1 >. subset y) -let _ = assert {msg="Failed subset"} (not (x.subset y)) - -# partionLt check -let _ = assert {msg="Failed partionLt"} - (fst (y.partionLt 2) >. toList == [0,1]) -let _ = assert {msg="Failed partionLt"} - (snd (y.partionLt 2) >. toList == [2,3]) - -# lowerBound check -let _ = assert {msg="Failed lowerBound"} - (match y.lowerBound with | Some x => x == 0 | _ => False end) - -# upperBound check -let _ = assert {msg="Failed upperBound"} - (match y.upperBound with | Some x => x == 3 | _ => False end) - From 2e8cf76e5dffb82221298498d385dd7af25aa161 Mon Sep 17 00:00:00 2001 From: Jakub Chomiczewski Date: Thu, 4 Dec 2025 13:21:30 +0100 Subject: [PATCH 27/27] Red Black Tree Comments --- lib/Queue.fram | 144 -------------------------- lib/RedBlackTree.fram | 166 +++++++++++++++++++++++++++--- test/stdlib/stdlib0005_Queue.fram | 24 ----- 3 files changed, 154 insertions(+), 180 deletions(-) delete mode 100644 lib/Queue.fram delete mode 100644 test/stdlib/stdlib0005_Queue.fram diff --git a/lib/Queue.fram b/lib/Queue.fram deleted file mode 100644 index 2c80ae40..00000000 --- a/lib/Queue.fram +++ /dev/null @@ -1,144 +0,0 @@ -{# This file is part of DBL, released under MIT license. - # See LICENSE for details. - #} - -import List - -data NotNegativeInt = Zero | Positive of Int - -let addOne value = - match value with - | Zero => Positive 1 - | Positive n => Positive (n+1) - end - -let subOne value = - match value with - | Zero => Zero - | Positive n => if n == 1 then Zero else Positive (n-1) - end - -data RotationState Val = - | Idle - | Reversing of NotNegativeInt, List Val, List Val, List Val, List Val - | Appending of NotNegativeInt, List Val, List Val - | Done of List Val - -data HoodMelvilleQueue Val = - | HMQueue of NotNegativeInt, List Val, RotationState Val, - NotNegativeInt, List Val - -let exec state = - match state with - | Reversing ok (x::f) f' (y::r) r' => - Reversing (addOne ok) f (x::f') r (y::r') - | Reversing ok [] f' [y] r' => Appending ok f' (y::r') - | Appending Zero f' r' => Done r' - | Appending ok (x::f') r' => Appending (subOne ok) f' (x::r') - | _ => state - end - -let invalidate state = - match state with - | Reversing ok f f' r r' => Reversing (subOne ok) f f' r r' - | Appending Zero f' (x::r') => Done r' - | Appending ok f' r' => Appending (subOne ok) f' r' - | _ => state - end - -let execTwice hmqueue = - match hmqueue with - | HMQueue lenf f state lenr r => - match exec (exec state) with - | Done newf => HMQueue lenf newf Idle lenr r - | newstate => HMQueue lenf f newstate lenr r - end - end - -let leq v1 v2 = - match (v1,v2) with - | (Zero,Zero) => True - | (Zero,Positive _) => True - | (Positive _, Zero) => False - | (Positive n, Positive m) => n <= m - end - -let add v1 v2 = - match (v1,v2) with - | (Zero,any) => any - | (any,Zero) => any - | (Positive n, Positive m) => Positive (n+m) - end - -let check queue = - match queue with - | HMQueue lenf f state lenr r => - if leq lenr lenf then execTwice queue - else ( - let newstate = Reversing Zero f [] r [] in - execTwice (HMQueue (add lenf lenr) f newstate Zero []) - ) - end - -pub let emptyQueue = HMQueue Zero [] Idle Zero [] -pub let isEmpty queue = - match queue with - | HMQueue Zero _ _ _ _ => True - | _ => False - end - -let snoc queue value = - match queue with - | HMQueue lenf f state lenr r => - check (HMQueue lenf f state (addOne lenr) (value :: r)) - end - -let head queue = - match queue with - | HMQueue Zero _ _ _ _ => None - | HMQueue _ (x::xs) _ _ _ => Some x - | _ => impossible () - end - -let tail queue = - match queue with - | HMQueue Zero _ _ _ _ => emptyQueue - | HMQueue _ [] _ _ _ => emptyQueue - | HMQueue lenf (x::xs) state lenr r => - check (HMQueue (subOne lenf) xs (invalidate state) lenr r) - end - -let mapRotationState f state = - match state with - | Idle => Idle - | Done list => Done (List.map f list) - | Appending v list1 list2 => - Appending v (List.map f list1) (List.map f list2) - | Reversing v list1 list2 list3 list4 => - Reversing v (List.map f list1) (List.map f list2) - (List.map f list3) (List.map f list4) - end - -let mapQueue queue f = - match queue with - | HMQueue v1 list1 state v2 list2 => - HMQueue v1 (List.map f list1) - (mapRotationState f state) v2 (List.map f list2) - end - -let rec toList queue = - match head queue with - | None => [] - | Some x => x :: toList (tail queue) - end - -pub let fromList list = List.foldLeft snoc emptyQueue list - -pub method isEmpty self = isEmpty self -pub method snoc self = snoc self -pub method tail self = tail self -pub method push self = snoc self -pub method pop self = tail self -pub method head self = head self -pub method map self = mapQueue self -pub method toList self = toList self diff --git a/lib/RedBlackTree.fram b/lib/RedBlackTree.fram index cd3cf0e3..010f13b9 100644 --- a/lib/RedBlackTree.fram +++ b/lib/RedBlackTree.fram @@ -10,6 +10,7 @@ import List data Color = | Red | Black + pub data rec Tree Value = | Leaf | Node of { @@ -19,25 +20,39 @@ pub data rec Tree Value = value: Value, right: Tree Value } + +{# Red-black invariant: +# no red node has a red child +# Black height invariant: +# for every t = Node(_, _, left, _, right), +# black-height(left) = black-height(right) +# Leaves are considered black, but do not contribute to black height. +#} + data ZipElem Value = | Left of Color, Value, Tree Value | Right of Color, Tree Value, Value +# Empty tree pub let empty = Leaf +# Return cached size pub let size tree = match tree with | Leaf => 0 | Node {size} => size end +# Smart constructor that updates the size of node pub let makeNode color left value right = Node {color, size = size left + size right + 1, left, value, right} +# Constructor for node pub let construct color size left value right = Node {color,size,left,value,right} -pub let rec zip tree zipper = +# Walk upward applying recorded decisions (zipper) to rebuild tree +let rec zip tree zipper = match zipper with | [] => tree @@ -49,16 +64,31 @@ pub let rec zip tree zipper = end -pub let rec zipRed value left right zipper = +{# Precondition: + # (zip (Node (RED, size, left, value ,right) zipper) + # satisfies the black-height invariant, + # and also satisfies the red-black + # invariant except possibly locally + #} +let rec zipRed value left right zipper = match zipper with + # Root case | [] => makeNode Black left value right - + + # Father is black and we are left child then we recreate the node + # and we are rebuilding tree | Left Black value1 right1 :: rest => zip (makeNode Black (makeNode Red left value right) value1 right1) rest + + # Father is black and we are right child then we recreate the node + # and we are rebuilding tree | Right Black left1 value1 :: rest => zip (makeNode Black left1 value1 (makeNode Red left value right)) rest + # Father is Red and left child, the uncle is Red and we are left child. + # The father and uncle are colored Black. + # ZipRed is recursively called on the grandfather. | Left Red value1 right1 :: Left _ value2 (Node {color = Red, size = size3, left = left3, @@ -67,6 +97,9 @@ pub let rec zipRed value left right zipper = let right' = construct Black size3 left3 value3 right3 in zipRed value2 (makeNode Black left' value1 right1) right' rest + # Father is Red and right child, the uncle is Red and we are left child. + # The father and uncle are colored Black. + # ZipRed is recursively called on the grandfather. | Left Red value1 right1 :: Right _ (Node {color = Red, size = size3, left = left3, @@ -75,6 +108,9 @@ pub let rec zipRed value left right zipper = let right' = makeNode Red left value right in zipRed value2 left' (makeNode Black right' value1 right1) rest + # Father is Red and left child, the uncle is Red and we are right child. + # The father and uncle are colored Black. + # ZipRed is recursively called on the grandfather. | Right Red left1 value1 :: Left _ value2 (Node {color = Red, size = size3, left = left3, @@ -83,6 +119,9 @@ pub let rec zipRed value left right zipper = let right' = construct Black size3 left3 value3 right3 in zipRed value2 (makeNode Black left1 value1 left') right' rest + # Father is Red and right child, the uncle is Red and we are right child. + # The father and uncle are colored Black. + # ZipRed is recursively called on the grandfather. | Right Red left1 value1 :: Right _ (Node {color = Red, size = size3, left = left3, value = value3, right = right3}) value2 :: rest => @@ -90,38 +129,68 @@ pub let rec zipRed value left right zipper = let right' = makeNode Red left value right in zipRed value2 left' (makeNode Black left1 value1 right') rest + # Father is Red and left child, the uncle is Black and we are left child. + # The father and uncle are colored Red. + # The grandfather is then black and we are rebuilding the tree. | Left Red value1 right1 :: Left _ value2 node3 :: rest => let left' = makeNode Red left value right let right' = makeNode Red right1 value2 node3 in zip (makeNode Black left' value1 right') rest - + + # Father is Red and right child, the uncle is Black and we are left child. + # The father and uncle are colored Red. + # The grandfather is then black and we are rebuilding the tree. | Left Red value1 right1 :: Right _ node3 value2 :: rest => let left' = makeNode Red node3 value2 left let right' = makeNode Red right value1 right1 in zip (makeNode Black left' value right') rest + # Father is Red and left child, the uncle is Black and we are right child. + # The father and uncle are colored Red. + # The grandfather is then black and we are rebuilding the tree. | Right Red left1 value1 :: Left _ value2 node3 :: rest => let left' = makeNode Red left1 value1 left let right' = makeNode Red right value2 node3 in zip (makeNode Black left' value right') rest + # Father is Red and right child, the uncle is Black and we are right child. + # The father and uncle are colored Red. + # The grandfather is then black and we are rebuilding the tree. | Right Red left1 value1 :: Right _ node3 value2 :: rest => let left' = makeNode Red node3 value2 left1 let right' = makeNode Red left value right in zip (makeNode Black left' value1 right') rest + # The father is Red and a root and we are left child. + # The functions correct invariant about root. | Left Red value1 right1 :: [] => makeNode Black (makeNode Red left value right) value1 right1 + # The father is Red and a root and we are right child. + # The functions correct invariant about root. | Right Red left1 value1 :: [] => makeNode Black left1 value1 (makeNode Red left value right) end +{# Precondition: +# 1. tree is black +# 2. (zip tree zipper) satisfies the red-black invariant, and it +# would satisfy the black-height invariant if the black-height of +# tree were one higher +#} pub let rec zipBlack tree zipper = match zipper with + # Root case | [] => tree + # Tree is left child, and right nephew is Red. + # father(C) brother(C) + # / \ / \ + # tree brother -> father(B) rnephew(B) + # / \ / \ + # lnephew rnephew(R) tree lnephew + # After rotation, the whole tree is reconstructed | Left color1 value1 (Node {left = left2, value = value2, right = (Node {color = Red, size = size3, @@ -131,13 +200,29 @@ pub let rec zipBlack tree zipper = let right' = construct Black size3 left3 value3 right3 in zip (makeNode color1 left' value2 right') rest + # Tree is right child, and left nephew is Red. + # Cfather Cbrother + # / \ / \ + # brother tree -> Blnephew Bfather + # / \ / \ + # Rlnephew rnephew rnephew tree + # After rotation, the whole tree is reconstructed | Right color1 (Node { left = (Node {color = Red, size = size3, left = left3, value = value3, right = right3}), value = value2, right = right2}) value1 :: rest => let left' = construct Black size3 left3 value3 right3 let right' = makeNode Black right2 value1 tree in zip (makeNode color1 left' value2 right') rest - + + # Tree is left child, and right nephew is Red. + # Cfather Crnephew + # / \ / \ + # tree brother -> Bfather Bbrother + # / \ / \ / \ + # Rlnephew Brnephew tree left right Brnephew + # / \ + # left right + # After rotation, the whole tree is reconstructed | Left color1 value1 (Node {left = (Node {color = Red, left = left3, value = value3, right = right3}), value = value2, right = right2}) :: rest => @@ -145,6 +230,15 @@ pub let rec zipBlack tree zipper = let right' = makeNode Black right3 value2 right2 in zip (makeNode color1 left' value3 right') rest + # Tree is right child, and left nephew is Red. + # Cfather Crnephew + # / \ / \ + # brother tree -> Bbrother Bfather + # / \ / \ / \ + # Blnephew Rrnephew Blnephew left right tree + # / \ + # left right + # After rotation, the whole tree is reconstructed | Right color1 (Node {left = left2, value = value2, right = (Node {color = Red, left = left3, value = value3, right = right3})}) value1 :: rest => @@ -152,30 +246,50 @@ pub let rec zipBlack tree zipper = let right' = makeNode Black right3 value1 tree in zip (makeNode color1 left' value3 right') rest + # The father is red and no nephew is red. + # Then father becomes black and brother becomes red + # removing therfore the inequality of blackness. + # After that, the whole tree is reconstructed. | Left Red value1 (Node {size = size2, left = left2, value = value2, right = right2}) :: rest => let right' = construct Red size2 left2 value2 right2 in zip (makeNode Black tree value1 right') rest + # The father is red and no nephew is red. + # Then father becomes black and brother becomes red + # removing therfore the inequality of blackness. + # After that, the whole tree is reconstructed. | Right Red (Node {size = size2, left = left2, value = value2, right = right2}) value1 :: rest => let left' = construct Red size2 left2 value2 right2 in zip (makeNode Black left' value1 tree) rest + # The father is black and no nephew is red. + # Brother becomes red but the inequality of blackness is sustained. + # ZipBlack recursively called on the father. | Left Black value1 (Node {color = Black, size = size2, left = left2, value = value2, right = right2}) :: rest => let right' = construct Red size2 left2 value2 right2 in zipBlack (makeNode Black tree value1 right') rest - + + # The father is black and no nephew is red. + # Brother becomes red but the inequality of blackness is sustained. + # ZipBlack recursively called on the father. | Right Black (Node {color = Black, size = size2, left = left2, value = value2, right = right2}) value1 :: rest => let left' = construct Red size2 left2 value2 right2 in zipBlack (makeNode Black left' value1 tree) rest + # The father is black and no nephew is red. + # Brother becomes red but the inequality of blackness is sustained. + # ZipBlack recursively called on the father. | Left Black value1 (Node {color = Red, left = left2, value = value2, right = right2}) :: rest => zipBlack tree (Left Red value1 left2 :: Left Black value2 right2 :: rest) + # The father is black and no nephew is red. + # Brother becomes red but the inequality of blackness is sustained. + # ZipBlack recursively called on the father. | Right Black (Node {color = Red, left = left2, value = value2, right = right2}) value1 :: rest => let rest' = Right Red right2 value1 :: Right Black left2 value2 :: rest in @@ -188,7 +302,8 @@ pub let rec zipBlack tree zipper = end -pub let rec search func tree zipper = +# search splits tree according to compare function and builds zipper +let rec search func tree zipper = match tree with | Leaf => (Leaf, zipper) | Node {color, left, value, right} => @@ -201,31 +316,46 @@ pub let rec search func tree zipper = end end -pub let rec searchMin tree zipper = +# serachMin finds smallest element in a tree and builds zipper +let rec searchMin tree zipper = match tree with | Leaf => zipper | Node {color, left, value, right} => searchMin left (Left color value right :: zipper) end -pub let rec searchMax tree zipper = +# serachMax finds largest element in a tree and builds zipper +let rec searchMax tree zipper = match tree with | Leaf => zipper | Node {color, left, value, right} => searchMax right (Right color left value:: zipper) end -pub let deleteNearLeaf color child zipper = +{# Removes a node if one of the child is a Leaf and rebuilds tree +# Precondition: +# (zip (Node (color, _, _, Leaf, child)) zipper) is a valid tree, +# or (zip (Node (color, _, _, child, Leaf)) zipper) is a valid tree. +#} +let deleteNearLeaf color child zipper = match color with + {# child cannot be RED, by red-black invariant, + so it must be Leaf, by black-height invariant. + #} | Red => zip Leaf zipper | Black => match child with | Node {value} => + # Must be RED with Leaf children, by black-height invariant. zip (makeNode Black Leaf value Leaf) zipper | Leaf => zipBlack Leaf zipper end end +{# Deletes node and adds children correctly to zipper and zip back the tree + Precondition: + zip (Node (color, _, _, left, right)) zipper is a valid tree. +#} pub let delete color left right zipper = match right with | Leaf => @@ -240,7 +370,7 @@ pub let delete color left right zipper = | Right colorLeftMin leftLeftMin valueLeftMin :: zipperr => deleteNearLeaf colorLeftMin leftLeftMin (List.append zipperr (Left color valueLeftMin right :: zipper)) - | _ => Leaf + | _ => Leaf #Fail "postcondition" end end | _ => @@ -248,10 +378,11 @@ pub let delete color left right zipper = | Left colorRightMin valueRightMin rightRightMin :: zipperr => deleteNearLeaf colorRightMin rightRightMin (List.append zipperr (Right color left valueRightMin :: zipper)) - | _ => Leaf + | _ => Leaf #Fail "postcondition" end end +# makes a root black pub let blacken tree = match tree with | Node {color = Red, size, left, value, right} => @@ -259,6 +390,7 @@ pub let blacken tree = | _ => tree end +# returns black height pub let rec blackHeight tree acc = match tree with | Leaf => acc @@ -266,6 +398,10 @@ pub let rec blackHeight tree acc = | Node {color=Black,left} => blackHeight left (1 + acc) end +{# precondition: blackHeight(tree) >= target >= 0 + find a black subtree along the left/right spine whose black-height is + blackHeight(tree) - target. +#} pub let rec searchHeight leftward target tree zipper = match tree with | Leaf => (Leaf, zipper) @@ -285,7 +421,9 @@ pub let rec searchHeight leftward target tree zipper = (Right Black left value :: zipper) end +# adds element to the tree pub let joinVal left value right = + # without loss of generality, assume left and right have black roots let left = blacken left in let right = blacken right in let lbh = blackHeight left 0 in @@ -294,11 +432,14 @@ pub let joinVal left value right = makeNode Black left value right else if lbh > rbh then (let (_left, zipper) = searchHeight False (lbh-rbh) left [] in + # left' and right are both black and both have black height rbh zipRed value _left right zipper) else (let (_right, zipper) = searchHeight True (rbh-lbh) right [] in + # left and right' are both black and both have black height lbh zipRed value left _right zipper) +# joins two trees pub let join left right = match left with | Leaf => right @@ -314,6 +455,7 @@ pub let join left right = end end +# Splits tree according to the function pub let rec split compareWithPivot tree = match tree with | Leaf => (None,Leaf,Leaf) diff --git a/test/stdlib/stdlib0005_Queue.fram b/test/stdlib/stdlib0005_Queue.fram deleted file mode 100644 index fb0fd636..00000000 --- a/test/stdlib/stdlib0005_Queue.fram +++ /dev/null @@ -1,24 +0,0 @@ -import Queue -import Prelude -import List - -let compare (x : Int) (y : Int) = x == y -let get_val x = -match x with -| Some x => x -| _ => -1 -end - -let x = Queue.emptyQueue -let x = x.push 1 -let _ = assert {msg="Failed push"} - (x.isEmpty == False && compare (get_val x.head) 1) -let x = x.pop -let _ = assert {msg="Failed isEmpty"} x.isEmpty -let x = x >. push 1 >. push 2 >. push 3 -let _ = assert {msg="Failed head and pop"} - (x.isEmpty == False && compare (get_val x.head) 1 && - compare (get_val (x.pop >. head)) 2 && - compare (get_val (x.pop >. pop >. head)) 3) -let x = Queue.fromList [1,2,3] -let _ = assert {msg="Failed toList and fromList"} (x.toList == [1,2,3]) \ No newline at end of file