1 | module Data.RRBVector
3 | import public Data.RRBVector.Internal
5 | import Control.Monad.ST
7 | import Data.Array.Core
8 | import Data.Array.Index
9 | import Data.Array.Indexed
14 | import Data.SnocList
16 | import Data.Zippable
17 | import Syntax.T1 as T1
20 | %hide Prelude.Ops.infixr.(<|)
21 | %hide Prelude.Ops.infixl.(|>)
53 | singleton x = Root 1 0 (Leaf $
A 1 $
fill 1 x)
61 | fromList [x] = singleton x
63 | case nodes Leaf xs of
65 | Root (treeSize 0 tree) 0 tree
67 | assert_smaller xs (iterateNodes blockshift xs')
69 | nodes : (Array a -> Tree a)
73 | let (trees', rest) = unsafeAlloc blocksize (go 0 blocksize f trees)
78 | (trees' :: nodes f (assert_smaller trees rest'))
81 | -> (Array a -> Tree a)
83 | -> WithMArray n a (Tree a,List a)
84 | go cur n f [] r = T1.do
85 | res <- unsafeFreeze r
86 | pure $
(f $
force $
take cur $
A n res,[])
87 | go cur n f (x :: xs) r =
90 | res <- unsafeFreeze r
91 | pure $
(f $
A n res, x :: xs)
93 | case tryNatToFin cur of
95 | assert_total $
idris_crash "Data.RRBVector.fromList.node: can't convert Nat to Fin"
99 | nodes' : (Array (Tree a) -> Tree a)
103 | let (trees', rest) = unsafeAlloc blocksize (go 0 blocksize f trees)
108 | (trees' :: nodes' f (assert_smaller trees rest'))
111 | -> (Array (Tree a) -> Tree a)
113 | -> WithMArray n (Tree a) (Tree a,List (Tree a))
114 | go cur n f [] r = T1.do
115 | res <- unsafeFreeze r
116 | pure $
(f $
force $
take cur $
A n res,[])
117 | go cur n f (x :: xs) r =
120 | res <- unsafeFreeze r
121 | pure $
(f $
A n res, x :: xs)
123 | case tryNatToFin cur of
125 | assert_total $
idris_crash "Data.RRBVector.fromList.node': can't convert Nat to Fin"
128 | go (S cur) n f xs r
132 | iterateNodes sh trees =
133 | case nodes' Balanced trees of
135 | Root (treeSize sh tree) sh tree
137 | iterateNodes (up sh) (assert_smaller trees trees')
146 | case compare n 0 of
152 | case compare n blocksize of
154 | Root n 0 (Leaf $
A n $
fill n x)
156 | Root n 0 (Leaf $
A n $
fill n x)
158 | let size' = integerToNat ((natToInteger $
minus n 1) .&. (natToInteger $
plus blockmask 1))
159 | in iterateNodes blockshift
160 | (Leaf $
A blocksize $
fill blocksize x)
161 | (Leaf $
A size' $
fill size' x)
163 | iterateNodes : Shift
167 | iterateNodes sh full rest =
168 | let subtreesm1 = (natToInteger $
minus n 1) `shiftR` sh
169 | restsize = integerToNat (subtreesm1 .&. (natToInteger blockmask))
170 | rest' = Balanced $
A (plus restsize 1) $
append (fill restsize full) (fill 1 rest)
171 | in case compare subtreesm1 (natToInteger blocksize) of
175 | let full' = Balanced (A blocksize $
fill blocksize full)
176 | in iterateNodes (up sh) (assert_smaller full full') (assert_smaller rest rest')
178 | let full' = Balanced (A blocksize $
fill blocksize full)
179 | in iterateNodes (up sh) (assert_smaller full full') (assert_smaller rest rest')
188 | toList : RRBVector a
191 | toList (Root _ _ tree) = treeToList tree
193 | treeToList : Tree a
195 | treeToList (Balanced trees) = assert_total $
concat (map treeToList (toList trees))
196 | treeToList (Unbalanced trees _) = assert_total $
concat (map treeToList (toList trees))
197 | treeToList (Leaf arr) = toList arr
204 | foldl : (b -> a -> b)
213 | foldlTree acc' (Balanced arr) = assert_total $
foldl foldlTree acc' arr
214 | foldlTree acc' (Unbalanced arr _) = assert_total $
foldl foldlTree acc' arr
215 | foldlTree acc' (Leaf arr) = assert_total $
foldl f acc' arr
219 | go (Root _ _ tree) = assert_total $
foldlTree acc tree
222 | foldr : (a -> b -> b)
231 | foldrTree (Balanced arr) acc' = assert_total $
foldr foldrTree acc' arr
232 | foldrTree (Unbalanced arr _) acc' = assert_total $
foldr foldrTree acc' arr
233 | foldrTree (Leaf arr) acc' = assert_total $
foldr f acc' arr
237 | go (Root _ _ tree) = assert_total $
foldrTree tree acc
254 | length : RRBVector a
257 | length (Root s _ _) = s
269 | lookup _ Empty = Nothing
270 | lookup i (Root size sh tree) =
271 | case compare i 0 of
275 | case compare i size of
281 | Just $
lookupTree i sh tree
283 | case compare i size of
289 | Just $
lookupTree i sh tree
295 | lookupTree i sh (Balanced arr) =
296 | case tryNatToFin (radixIndex i sh) of
298 | assert_total $
idris_crash "Data.RRBVector.lookup: can't convert Nat to Fin"
300 | assert_total $
lookupTree i (down sh) (at arr.arr i')
301 | lookupTree i sh (Unbalanced arr sizes) =
302 | let (idx, subidx) = relaxedRadixIndex sizes i sh
303 | in case tryNatToFin idx of
305 | assert_total $
idris_crash "Data.RRBVector.lookup: can't convert Nat to Fin"
307 | assert_total $
lookupTree subidx (down sh) (at arr.arr idx')
308 | lookupTree i _ (Leaf arr) =
309 | let i' = integerToNat ((natToInteger i) .&. (natToInteger blockmask))
310 | in case tryNatToFin i' of
312 | assert_total $
idris_crash "Data.RRBVector.lookup: can't convert Nat to Fin"
323 | index i = fromMaybe (assert_total $
idris_crash "Data.RRBVector.index: index out of range") . lookup i
349 | update _ _ Empty = Empty
350 | update i x v@(Root size sh tree) =
351 | case compare i 0 of
355 | case compare i size of
361 | Root size sh (updateTree i sh tree)
363 | case compare i size of
369 | Root size sh (updateTree i sh tree)
375 | updateTree i sh (Balanced arr) =
376 | case tryNatToFin (radixIndex i sh) of
378 | assert_total $
idris_crash "Data.RRBVector.update: can't convert Nat to Fin"
380 | assert_total $
Balanced (A arr.size (updateAt i' (updateTree i (down sh)) arr.arr))
381 | updateTree i sh (Unbalanced arr sizes) =
382 | let (idx, subidx) = relaxedRadixIndex sizes i sh
383 | in case tryNatToFin idx of
385 | assert_total $
idris_crash "Data.RRBVector.update: can't convert Nat to Fin"
387 | assert_total $
Unbalanced (A arr.size (updateAt idx' (updateTree subidx (down sh)) arr.arr)) sizes
388 | updateTree i _ (Leaf arr) =
389 | let i' = integerToNat ((natToInteger i) .&. (natToInteger blockmask))
390 | in case tryNatToFin i' of
392 | assert_total $
idris_crash "Data.RRBVector.update: can't convert Nat to Fin"
394 | Leaf (A arr.size (setAt i'' x arr.arr))
404 | adjust _ _ Empty = Empty
405 | adjust i f v@(Root size sh tree) =
406 | case compare i 0 of
410 | case compare i size of
416 | Root size sh (adjustTree i sh tree)
418 | case compare i size of
424 | Root size sh (adjustTree i sh tree)
430 | adjustTree i sh (Balanced arr) =
431 | case tryNatToFin (radixIndex i sh) of
433 | assert_total $
idris_crash "Data.RRBVector.adjust: can't convert Nat to Fin"
435 | assert_total $
Balanced (A arr.size (updateAt i' (adjustTree i (down sh)) arr.arr))
436 | adjustTree i sh (Unbalanced arr sizes) =
437 | let (idx, subidx) = relaxedRadixIndex sizes i sh
438 | in case tryNatToFin idx of
440 | assert_total $
idris_crash "Data.RRBVector.adjust: can't convert Nat to Fin"
442 | assert_total $
Unbalanced (A arr.size (updateAt idx' (adjustTree subidx (down sh)) arr.arr)) sizes
443 | adjustTree i _ (Leaf arr) =
444 | let i' = integerToNat ((natToInteger i) .&. (natToInteger blockmask))
445 | in case tryNatToFin i' of
447 | assert_total $
idris_crash "Data.RRBVector.adjust: can't convert Nat to Fin"
449 | Leaf (A arr.size (updateAt i'' f arr.arr))
452 | normalize : RRBVector a
454 | normalize v@(Root size sh (Balanced arr)) =
455 | case compare arr.size 1 of
459 | case tryNatToFin 0 of
461 | assert_total $
idris_crash "Data.RRBVector.normalize: can't convert Nat to Fin"
463 | assert_total $
normalize $
Root size (down sh) (at arr.arr i)
466 | normalize v@(Root size sh (Unbalanced arr _)) =
467 | case compare arr.size 1 of
471 | case tryNatToFin 0 of
473 | assert_total $
idris_crash "Data.RRBVector.normalize: can't convert Nat to Fin"
475 | assert_total $
normalize $
Root size (down sh) (at arr.arr i)
488 | takeTree i sh (Balanced arr) with (radixIndex i sh) | ((plus (radixIndex i sh) 1) <= arr.size) proof eq
490 | case tryNatToFin i' of
492 | assert_total $
idris_crash "Data.RRBVector.takeTree: can't convert Nat to Fin"
494 | let newarr = force $
take (plus (radixIndex i sh) 1) arr.arr @{lteOpReflectsLTE _ _ eq}
495 | in assert_total $
Balanced (A (plus (radixIndex i sh) 1) (updateAt i'' (takeTree i (down sh)) newarr))
497 | assert_total $
idris_crash "Data.RRBVector.takeTree: index out of bounds"
498 | takeTree i sh (Unbalanced arr sizes) with (relaxedRadixIndex sizes i sh) | ((plus (fst (relaxedRadixIndex sizes i sh)) 1) <= arr.size) proof eq
499 | _ | (idx, subidx) | True =
500 | case tryNatToFin idx of
502 | assert_total $
idris_crash "Data.RRBVector.takeTree: can't convert Nat to Fin"
504 | let newarr = force $
take (plus (fst (relaxedRadixIndex sizes i sh)) 1) arr.arr @{lteOpReflectsLTE _ _ eq}
505 | in assert_total $
computeSizes sh (A (plus (fst (relaxedRadixIndex sizes i sh)) 1) (updateAt idx' (takeTree subidx (down sh)) newarr))
507 | assert_total $
idris_crash "Data.RRBVector.takeTree: index out of bounds"
508 | takeTree i _ (Leaf arr) with (integerToNat (((natToInteger i) .&. (natToInteger blockmask)) + 1) <= arr.size) proof eq
510 | let newarr = force $
take (integerToNat (((natToInteger i) .&. (natToInteger blockmask)) + 1)) arr.arr @{lteOpReflectsLTE _ _ eq}
511 | in Leaf (A (integerToNat (((natToInteger i) .&. (natToInteger blockmask)) + 1)) newarr)
513 | assert_total $
idris_crash "Data.RRBVector.takeTree: index out of bounds"
520 | dropTree n sh (Balanced arr) =
521 | case tryNatToFin 0 of
523 | assert_total $
idris_crash "Data.RRBVector.dropTree: can't convert Nat to Fin"
525 | let newarr = force $
drop (radixIndex n sh) arr.arr
526 | in assert_total $
computeSizes sh (A (minus arr.size (radixIndex n sh)) (updateAt zero (dropTree n (down sh)) newarr))
527 | dropTree n sh (Unbalanced arr sizes) =
528 | case tryNatToFin 0 of
530 | assert_total $
idris_crash "Data.RRBVector.dropTree: can't convert Nat to Fin"
532 | let newarr = force $
drop (fst $
relaxedRadixIndex sizes n sh) arr.arr
533 | in assert_total $
computeSizes sh (A (minus arr.size (fst $
relaxedRadixIndex sizes n sh)) (updateAt zero (dropTree (snd $
relaxedRadixIndex sizes n sh) (down sh)) newarr))
534 | dropTree n _ (Leaf arr) =
535 | let n = integerToNat ((natToInteger n) .&. (natToInteger blockmask))
536 | newarr = force $
drop n arr.arr
537 | in Leaf (A (minus arr.size n) newarr)
546 | take _ Empty = Empty
547 | take n v@(Root size sh tree) =
548 | case compare n 0 of
554 | case compare n size of
556 | normalize $
Root n sh (takeTree (minus n 1) sh tree)
569 | drop _ Empty = Empty
570 | drop n v@(Root size sh tree) =
571 | case compare n 0 of
577 | case compare n size of
579 | normalize $
Root (minus size n) sh (dropTree n sh tree)
590 | -> (RRBVector a, RRBVector a)
591 | splitAt _ Empty = (Empty, Empty)
592 | splitAt n v@(Root size sh tree) =
593 | case compare n 0 of
599 | case compare n size of
601 | let left = normalize $
Root n sh (takeTree (minus n 1) sh tree)
602 | right = normalize $
Root (minus size n) sh (dropTree n sh tree)
616 | viewl : RRBVector a
617 | -> Maybe (a, RRBVector a)
618 | viewl Empty = Nothing
619 | viewl v@(Root _ _ tree) =
620 | let tail = drop 1 v
621 | in Just (headTree tree, tail)
623 | headTree : Tree a -> a
624 | headTree (Balanced arr) =
625 | case tryNatToFin 0 of
627 | assert_total $
idris_crash "Data.RRBVector.viewl: can't convert Nat to Fin"
629 | assert_total $
headTree (at arr.arr zero)
630 | headTree (Unbalanced arr _) =
631 | case tryNatToFin 0 of
633 | assert_total $
idris_crash "Data.RRBVector.viewl: can't convert Nat to Fin"
635 | assert_total $
headTree (at arr.arr zero)
636 | headTree (Leaf arr) =
637 | case tryNatToFin 0 of
639 | assert_total $
idris_crash "Data.RRBVector.viewl: can't convert Nat to Fin"
646 | viewr : RRBVector a
647 | -> Maybe (RRBVector a, a)
648 | viewr Empty = Nothing
649 | viewr v@(Root size _ tree) =
650 | let init = take (minus size 1) v
651 | in Just (init, lastTree tree)
653 | lastTree : Tree a -> a
654 | lastTree (Balanced arr) =
655 | case tryNatToFin (minus size 1) of
657 | assert_total $
idris_crash "Data.RRBVector.viewr: can't convert Nat to Fin"
659 | assert_total $
lastTree (at arr.arr last)
660 | lastTree (Unbalanced arr _) =
661 | case tryNatToFin (minus size 1) of
663 | assert_total $
idris_crash "Data.RRBVector.viewr: can't convert Nat to Fin"
665 | assert_total $
lastTree (at arr.arr last)
666 | lastTree (Leaf arr) =
667 | case tryNatToFin (minus size 1) of
669 | assert_total $
idris_crash "Data.RRBVector.viewr: can't convert Nat to Fin"
683 | map _ Empty = Empty
684 | map f (Root size sh tree) = Root size sh (mapTree tree)
686 | mapTree : Tree a -> Tree b
687 | mapTree (Balanced arr) =
688 | assert_total $
Balanced (map mapTree arr)
689 | mapTree (Unbalanced arr sizes) =
690 | assert_total $
Unbalanced (map mapTree arr) sizes
691 | mapTree (Leaf arr) =
697 | reverse : RRBVector a
700 | case compare (length v) 1 of
706 | case fromList $
toList v of
708 | assert_total $
idris_crash "Data.RRBVector.reverse: can't convert to List1"
710 | fromList $
forget $
reverse v'
718 | -> RRBVector (a, b)
720 | case fromList $
toList v1 of
722 | assert_total $
idris_crash "Data.RRBVector.zip: can't convert to List1"
724 | case fromList $
toList v2 of
726 | assert_total $
idris_crash "Data.RRBVector.zip: can't convert to List1"
728 | fromList $
forget $
zip v1' v2'
740 | newBranch x 0 = Leaf (singleton x)
741 | newBranch x sh = assert_total $
Balanced (singleton $
newBranch x (down sh))
749 | x <| Empty = singleton x
750 | x <| Root size sh tree =
751 | case compare insertshift sh of
753 | Root (plus size 1) sh (consTree sh tree)
755 | Root (plus size 1) sh (consTree sh tree)
757 | let new = A 2 $
array $
fromList [(newBranch x sh), tree]
758 | in Root (plus size 1) insertshift (computeSizes insertshift new)
767 | computeShift sz sh min (Balanced _) =
769 | let hishift = let comp = mult (log2 (minus sz 1) `div` blockshift) blockshift
770 | in case compare comp 0 of
777 | hi = (natToInteger $
minus sz 1) `shiftR` hishift
778 | newshift = case compare hi (natToInteger blockmask) of
782 | plus hishift blockshift
784 | plus hishift blockshift
785 | in case compare newshift sh of
792 | computeShift _ sh min (Unbalanced arr sizes) =
793 | let sz' = case tryNatToFin 0 of
795 | assert_total $
idris_crash "Data.RRBVector.(<|).computeShift.Unbalanced: can't convert Nat to Fin"
798 | newtree = case tryNatToFin 0 of
800 | assert_total $
idris_crash "Data.RRBVector.(<|).computeShift.Unbalanced: can't convert Nat to Fin"
803 | newmin = case compare arr.size blocksize of
810 | in assert_total $
computeShift sz' (down sh) newmin newtree
811 | computeShift _ _ min (Leaf arr) =
812 | case compare arr.size blocksize of
820 | insertshift = computeShift size sh (up sh) tree
824 | consTree sh (Balanced arr) =
825 | case compare sh insertshift of
827 | case tryNatToFin 0 of
829 | assert_total $
idris_crash "Data.RRBVector.(<|).consTree.Balanced: can't convert Nat to Fin"
831 | assert_total $
computeSizes sh (A arr.size $
updateAt zero (consTree (down sh)) arr.arr)
833 | computeSizes sh (A (S arr.size) (append (fill 1 (newBranch x (down sh))) arr.arr))
835 | case tryNatToFin 0 of
837 | assert_total $
idris_crash "Data.RRBVector.(<|).consTree.Balanced: can't convert Nat to Fin"
839 | assert_total $
computeSizes sh (A arr.size $
updateAt zero (consTree (down sh)) arr.arr)
840 | consTree sh (Unbalanced arr _) =
841 | case compare sh insertshift of
843 | case tryNatToFin 0 of
845 | assert_total $
idris_crash "Data.RRBVector.(<|).consTree.Unbalanced: can't convert Nat to Fin"
847 | assert_total $
computeSizes sh (A arr.size $
updateAt zero (consTree (down sh)) arr.arr)
849 | computeSizes sh (A (S arr.size) (append (fill 1 (newBranch x (down sh))) arr.arr))
851 | case tryNatToFin 0 of
853 | assert_total $
idris_crash "Data.RRBVector.(<|).consTree.Unbalanced: can't convert Nat to Fin"
855 | assert_total $
computeSizes sh (A arr.size $
updateAt zero (consTree (down sh)) arr.arr)
856 | consTree _ (Leaf arr) =
857 | Leaf (A (S arr.size) (append (fill 1 x) arr.arr))
865 | Empty |> x = singleton x
866 | Root size sh tree |> x =
867 | case compare insertshift sh of
869 | Root (plus size 1) sh (snocTree sh tree)
871 | Root (plus size 1) sh (snocTree sh tree)
873 | let new = A 2 $
array $
fromList [tree,(newBranch x sh)]
874 | in Root (plus size 1) insertshift (computeSizes insertshift new)
883 | computeShift sz sh min (Balanced _) =
885 | let newshift = mult (countTrailingZeros sz `div` blockshift) blockshift
886 | in case compare newshift sh of
893 | computeShift _ sh min (Unbalanced arr sizes) =
894 | let lastidx = minus arr.size 1
895 | sz' = case tryNatToFin lastidx of
897 | assert_total $
idris_crash "Data.RRBVector.(|>).computeShift.Unbalanced: can't convert Nat to Fin"
899 | case tryNatToFin $
minus lastidx 1 of
901 | assert_total $
idris_crash "Data.RRBVector.(|>).computeShift.Unbalanced: can't convert Nat to Fin"
903 | minus (at sizes.arr lastidx') (at sizes.arr lastidx'')
904 | newtree = case tryNatToFin lastidx of
906 | assert_total $
idris_crash "Data.RRBVector.(|>).computeShift.Unbalanced: can't convert Nat to Fin"
908 | at arr.arr lastidx'
909 | newmin = case compare arr.size blocksize of
916 | in assert_total $
computeShift sz' (down sh) newmin newtree
917 | computeShift _ _ min (Leaf arr) =
918 | case compare arr.size blocksize of
926 | insertshift = computeShift size sh (up sh) tree
930 | snocTree sh (Balanced arr) =
931 | case compare sh insertshift of
933 | case tryNatToFin $
minus arr.size 1 of
935 | assert_total $
idris_crash "Data.RRBVector.(|>).snocTree.Balanced: can't convert Nat to Fin"
937 | assert_total $
Balanced (A arr.size $
updateAt lastidx (snocTree (down sh)) arr.arr)
939 | Balanced (A (plus arr.size 1) (append arr.arr (fill 1 (newBranch x (down sh)))))
941 | case tryNatToFin $
minus arr.size 1 of
943 | assert_total $
idris_crash "Data.RRBVector.(|>).snocTree.Balanced: can't convert Nat to Fin"
945 | assert_total $
Balanced (A arr.size $
updateAt lastidx (snocTree (down sh)) arr.arr)
946 | snocTree sh (Unbalanced arr sizes) =
947 | case compare sh insertshift of
949 | case tryNatToFin $
minus arr.size 1 of
951 | assert_total $
idris_crash "Data.RRBVector.(|>).snocTree.Unbalanced: can't convert Nat to Fin"
953 | case tryNatToFin $
minus sizes.size 1 of
955 | assert_total $
idris_crash "Data.RRBVector.(|>).snocTree.Unbalanced: can't convert Nat to Fin"
957 | let lastsize = plus (at sizes.arr lastidxs) 1
958 | in assert_total $
Unbalanced (A arr.size (updateAt lastidxa (snocTree (down sh)) arr.arr))
959 | (A sizes.size (setAt lastidxs lastsize sizes.arr))
961 | case tryNatToFin $
minus sizes.size 1 of
963 | assert_total $
idris_crash "Data.RRBVector.(|>).snocTree.Unbalanced: can't convert Nat to Fin"
965 | let lastsize = plus (at sizes.arr lastidx) 1
966 | in assert_total $
Unbalanced (A (plus arr.size 1) (append arr.arr (fill 1 (newBranch x (down sh)))))
967 | (A (plus sizes.size 1) (append sizes.arr (fill 1 lastsize)))
969 | case tryNatToFin $
minus arr.size 1 of
971 | assert_total $
idris_crash "Data.RRBVector.(|>).snocTree.Unbalanced: can't convert Nat to Fin"
973 | case tryNatToFin $
minus sizes.size 1 of
975 | assert_total $
idris_crash "Data.RRBVector.(|>).snocTree.Unbalanced: can't convert Nat to Fin"
977 | let lastsize = plus (at sizes.arr lastidxs) 1
978 | in assert_total $
Unbalanced (A arr.size (updateAt lastidxa (snocTree (down sh)) arr.arr))
979 | (A sizes.size (setAt lastidxs lastsize sizes.arr))
980 | snocTree _ (Leaf arr) = Leaf (A (plus arr.size 1) (append arr.arr (fill 1 x)))
990 | Root size1 sh1 tree1 >< Root size2 sh2 tree2 =
991 | let upmaxshift = case compare sh1 sh2 of
998 | newarr = mergeTrees tree1 sh1 tree2 sh2
999 | in normalize $
Root (plus size1 size2) upmaxshift (computeSizes upmaxshift newarr)
1001 | viewlArr : Array (Tree a) -> (Tree a, Array (Tree a))
1005 | assert_total $
idris_crash "Data.RRBVector.(><).viewlArr: can't convert Nat to Fin"
1007 | (at arr.arr zero, drop 1 arr)
1008 | viewrArr : Array (Tree b) -> (Array (Tree b), Tree b)
1010 | case tryNatToFin $
minus arr.size 1 of
1012 | assert_total $
idris_crash "Data.RRBVector.(><).viewrArr: can't convert Nat to Fin"
1014 | (take (minus arr.size 1) arr, at arr.arr last)
1015 | mergeRebalance' : Shift
1019 | -> (Tree a -> Array (Tree a))
1020 | -> (Array (Tree a) -> Tree a)
1022 | mergeRebalance' sh left center right extract construct =
1024 | nodecounter <- newSTRef 0
1025 | subtreecounter <- newSTRef 0
1026 | newnode <- newSTRef Lin
1027 | newsubtree <- newSTRef Lin
1028 | newroot <- newSTRef Lin
1029 | for_ (toList left ++ toList center ++ toList right) $
\subtree =>
1030 | for_ (extract subtree) $
\x => do
1031 | nodecounter' <- readSTRef nodecounter
1032 | when (nodecounter' == (natToInteger blocksize)) $
do
1033 | newnode' <- readSTRef newnode
1034 | modifySTRef newsubtree (\y => y :< (construct $
A (SnocSize newnode')
1038 | writeSTRef nodecounter 0
1039 | modifySTRef subtreecounter (\y => y + 1
1041 | subtreecounter' <- readSTRef subtreecounter
1042 | when (subtreecounter' == (natToInteger blocksize)) $
do
1043 | newsubtree' <- readSTRef newsubtree
1044 | modifySTRef newroot (\y => y :< (computeSizes sh (fromList $
the (List (Tree a)) (cast newsubtree')))
1046 | writeSTRef newsubtree Lin
1047 | writeSTRef subtreecounter 0
1048 | modifySTRef newnode (\y => y :< (fill 1 x)
1050 | modifySTRef nodecounter (\y => y + 1
1052 | newnode' <- readSTRef newnode
1053 | modifySTRef newsubtree (\y => y :< (construct $
A (SnocSize newnode')
1056 | newsubtree' <- readSTRef newsubtree
1057 | modifySTRef newroot (\y => y :< (computeSizes sh (fromList $
the (List (Tree a)) (cast newsubtree')))
1059 | newroot' <- readSTRef newroot
1060 | pure $
fromList $
the (List (Tree a)) (cast newroot')
1061 | mergeRebalance'' : Shift
1068 | mergeRebalance'' sh left center right extract construct =
1070 | nodecounter <- newSTRef 0
1071 | subtreecounter <- newSTRef 0
1072 | newnode <- newSTRef Lin
1073 | newsubtree <- newSTRef Lin
1074 | newroot <- newSTRef Lin
1075 | for_ (toList left ++ toList center ++ toList right) $
\subtree =>
1076 | for_ (extract subtree) $
\x => do
1077 | nodecounter' <- readSTRef nodecounter
1078 | when (nodecounter' == (natToInteger blocksize)) $
do
1079 | newnode' <- readSTRef newnode
1080 | modifySTRef newsubtree (\y => y :< (construct $
A (SnocSize newnode')
1084 | writeSTRef nodecounter 0
1085 | modifySTRef subtreecounter (\y => y + 1
1087 | subtreecounter' <- readSTRef subtreecounter
1088 | when (subtreecounter' == (natToInteger blocksize)) $
do
1089 | newsubtree' <- readSTRef newsubtree
1090 | modifySTRef newroot (\y => y :< (computeSizes sh (fromList $
the (List (Tree a)) (cast newsubtree')))
1092 | writeSTRef newsubtree Lin
1093 | writeSTRef subtreecounter 0
1094 | modifySTRef newnode (\y => y :< (fill 1 x)
1096 | modifySTRef nodecounter (\y => y + 1
1098 | newnode' <- readSTRef newnode
1099 | modifySTRef newsubtree (\y => y :< (construct $
A (SnocSize newnode')
1102 | newsubtree' <- readSTRef newsubtree
1103 | modifySTRef newroot (\y => y :< (computeSizes sh (fromList $
the (List (Tree a)) (cast newsubtree')))
1105 | newroot' <- readSTRef newroot
1106 | pure $
fromList $
the (List (Tree a)) (cast newroot')
1112 | mergeRebalance sh left center right =
1113 | case compare sh blockshift of
1115 | assert_total $
mergeRebalance' sh left center right treeToArray (computeSizes (down sh))
1117 | assert_total $
mergeRebalance'' sh left center right (\(Leaf arr) => arr) Leaf
1119 | assert_total $
mergeRebalance' sh left center right treeToArray (computeSizes (down sh))
1125 | mergeTrees tree1@(Leaf arr1) _ tree2@(Leaf arr2) _ =
1126 | case compare arr1.size blocksize of
1128 | let arr' = A (plus arr1.size arr2.size) (append arr1.arr arr2.arr)
1129 | in case compare arr'.size blocksize of
1135 | let (left, right) = (take blocksize arr',drop blocksize arr')
1138 | in A 2 $
fromPairs 2 lefttree [(1,righttree)]
1140 | A 2 $
fromPairs 2 tree1 [(1,tree2)]
1142 | let arr' = A (plus arr1.size arr2.size) (append arr1.arr arr2.arr)
1143 | in case compare arr'.size blocksize of
1149 | let (left, right) = (take blocksize arr',drop blocksize arr')
1152 | in A 2 $
fromPairs 2 lefttree [(1,righttree)]
1153 | mergeTrees tree1 sh1 tree2 sh2 =
1154 | case compare sh1 sh2 of
1156 | let right = treeToArray tree2
1157 | (righthead, righttail) = viewlArr right
1158 | merged = assert_total $
mergeTrees tree1 sh1 righthead (down sh2)
1159 | in mergeRebalance sh2 empty merged righttail
1161 | let left = treeToArray tree1
1162 | (leftinit, leftlast) = viewrArr left
1163 | merged = assert_total $
mergeTrees leftlast (down sh1) tree2 sh2
1164 | in mergeRebalance sh1 leftinit merged empty
1166 | let left = treeToArray tree1
1167 | right = treeToArray tree2
1168 | (leftinit, leftlast) = viewrArr left
1169 | (righthead, righttail) = viewlArr right
1170 | merged = assert_total $
mergeTrees leftlast (down sh1) righthead (down sh2)
1171 | in mergeRebalance sh1 leftinit merged righttail
1183 | let (left, right) = splitAt i v
1184 | in (left |> x) >< right
1194 | let (left, right) = splitAt (plus i 1) v
1195 | in take i left >< right
1204 | showRRBVectorRep : Show a
1209 | showRRBVectorRep Empty =
1211 | showRRBVectorRep (Root size sh t) =
1227 | Eq a => Eq (RRBVector a) where
1228 | xs == ys = length xs == length ys && Data.RRBVector.toList xs == Data.RRBVector.toList ys
1231 | Ord a => Ord (RRBVector a) where
1232 | compare xs ys = compare (Data.RRBVector.toList xs) (Data.RRBVector.toList ys)
1235 | Functor RRBVector where
1239 | Foldable RRBVector where
1240 | foldl f z = Data.RRBVector.foldl f z
1241 | foldr f z = Data.RRBVector.foldr f z
1245 | Applicative RRBVector where
1247 | fs <*> xs = Data.RRBVector.foldl (\acc, f => acc >< map f xs) empty fs
1250 | Semigroup (RRBVector a) where
1254 | Semigroup (RRBVector a) => Monoid (RRBVector a) where
1259 | xs >>= f = Data.RRBVector.foldl (\acc, x => acc >< f x) empty xs