0 | module Data.Array.Indexed
2 | import Data.Array.Mutable
5 | import Data.Linear.Traverse1
6 | import Syntax.PreorderReasoning
15 | record Array a where
26 | ix : IArray n a -> (0 m : Nat) -> {auto x: Ix (S m) n} -> a
27 | ix arr _ = at arr (ixToFin x)
31 | atNat : IArray n a -> (m : Nat) -> {auto 0 lt : LT m n} -> a
32 | atNat arr x = at arr (natToFinLT x)
41 | empty = unsafeAlloc 0 unsafeFreeze
45 | arrayL : (ls : List a) -> IArray (length ls) a
46 | arrayL xs = allocList xs unsafeFreeze
50 | array : {n : _} -> Vect n a -> IArray n a
51 | array xs = allocVect xs unsafeFreeze
59 | revArray : {n : _} -> Vect n a -> IArray n a
60 | revArray xs = allocVectRev xs unsafeFreeze
64 | fill : (n : Nat) -> a -> IArray n a
65 | fill n v = alloc n v unsafeFreeze
70 | generate : (n : Nat) -> (Fin n -> a) -> IArray n a
71 | generate n f = allocGen n f unsafeFreeze
76 | iterate : (n : Nat) -> (f : a -> a) -> a -> IArray n a
77 | iterate n f v = allocIter n f v unsafeFreeze
85 | force : {n : _} -> IArray n a -> IArray n a
86 | force arr = generate n (at arr)
91 | fromPairs : (n : Nat) -> a -> List (Nat,a) -> IArray n a
92 | fromPairs n v ps = alloc n v (go ps)
94 | go : List (Nat,a) -> WithMArray n a (IArray n a)
95 | go [] r = unsafeFreeze r
96 | go ((x,v) :: xs) r =
97 | case tryNatToFin x of
98 | Just y => T1.do
set r y v;
go xs r
103 | fromFinPairs : (n : Nat) -> a -> List (Fin n,a) -> IArray n a
104 | fromFinPairs n v ps = alloc n v (go ps)
106 | go : List (Fin n,a) -> WithMArray n a (IArray n a)
107 | go [] r = unsafeFreeze r
108 | go ((x,v) :: xs) r = T1.do
set r x v;
go xs r
117 | unsafeJSArrayOf1 : (0 a : Type) -> AnyPtr -> F1 s (Array a)
118 | unsafeJSArrayOf1 a ptr t =
119 | let (
n ** marr)
# t := unsafeJSMArrayOf1 a ptr t
120 | iarr # t := freeze marr t
125 | unsafeJSArrayOf : HasIO io => (0 a : Type) -> AnyPtr -> io (Array a)
126 | unsafeJSArrayOf a ptr = runIO (unsafeJSArrayOf1 a ptr)
134 | unsafeWrapJSArray : (0 a : Type) -> AnyPtr -> Array a
135 | unsafeWrapJSArray a ptr =
137 | let (
n ** marr)
# t := unsafeJSMArrayOf1 a ptr t
138 | iarr # t := unsafeFreeze marr t
147 | hcomp : {m,n : Nat} -> Ord a => IArray m a -> IArray n a -> Ordering
148 | hcomp a1 a2 = go m n
151 | go : (k,l : Nat) -> {auto _ : Ix k m} -> {auto _ : Ix l n} -> Ordering
155 | go (S k) (S j) = case compare (ix a1 k) (ix a2 j) of
161 | heq : {m,n : Nat} -> Eq a => IArray m a -> IArray n a -> Bool
165 | go : (k,l : Nat) -> {auto _ : Ix k m} -> {auto _ : Ix l n} -> Bool
167 | go (S k) (S j) = if ix a1 k == ix a2 j then go k j else False
171 | {n : Nat} -> Eq a => Eq (IArray n a) where
175 | go : (k : Nat) -> {auto 0 _ : LTE k n} -> Bool
177 | go (S k) = if atNat a1 k == atNat a2 k then go k else False
180 | {n : Nat} -> Ord a => Ord (IArray n a) where
181 | compare a1 a2 = go n
184 | go : (k : Nat) -> {auto _ : Ix k n} -> Ordering
186 | go (S k) = case compare (ix a1 k) (ix a2 k) of
194 | ontoList : List a -> (m : Nat) -> (0 lte : LTE m n) => IArray n a -> List a
195 | ontoList xs 0 arr = xs
196 | ontoList xs (S k) arr = ontoList (atNat arr k :: xs) k arr
201 | -> {auto 0 lte : LTE m n}
204 | ontoVect xs 0 arr = rewrite plusZeroRightNeutral k in xs
205 | ontoVect xs (S v) arr =
206 | rewrite sym (plusSuccRightSucc k v) in ontoVect (atNat arr v :: xs) v arr
208 | ontoVectWithIndex :
211 | -> {auto 0 lte : LTE m n}
213 | -> Vect (k + m) (Fin n, a)
214 | ontoVectWithIndex xs 0 arr = rewrite plusZeroRightNeutral k in xs
215 | ontoVectWithIndex xs (S v) arr =
216 | rewrite sym (plusSuccRightSucc k v)
217 | in let x := natToFinLT v in ontoVectWithIndex ((x, at arr x) :: xs) v arr
221 | toVect : {n : _} -> IArray n a -> Vect n a
222 | toVect = ontoVect [] n
227 | toVectWithIndex : {n : _} -> IArray n a -> Vect n (Fin n, a)
228 | toVectWithIndex = ontoVectWithIndex [] n
230 | foldrI : (m : Nat) -> (0 _ : LTE m n) => (e -> a -> a) -> a -> IArray n e -> a
231 | foldrI 0 _ x arr = x
232 | foldrI (S k) f x arr = foldrI k f (f (atNat arr k) x) arr
236 | -> {auto 0 prf : LTE m n}
237 | -> (Fin n -> e -> a -> a)
240 | foldrKV_ 0 _ x arr = x
241 | foldrKV_ (S k) f x arr =
242 | let fin := natToFinLT k @{prf} in foldrKV_ k f (f fin (at arr fin) x) arr
244 | foldlI : (m : Nat) -> (x : Ix m n) => (a -> e -> a) -> a -> IArray n e -> a
245 | foldlI 0 _ v arr = v
246 | foldlI (S k) f v arr = foldlI k f (f v (ix arr k)) arr
250 | -> {auto x : Ix m n}
251 | -> (Fin n -> a -> e -> a)
255 | foldlKV_ 0 _ v arr = v
256 | foldlKV_ (S k) f v arr =
257 | let fin := ixToFin x in foldlKV_ k f (f fin v (at arr fin)) arr
261 | foldrKV : {n : _} -> (Fin n -> e -> a -> a) -> a -> IArray n e -> a
262 | foldrKV = foldrKV_ n
266 | foldlKV : {n : _} -> (Fin n -> a -> e -> a) -> a -> IArray n e -> a
267 | foldlKV = foldlKV_ n
270 | {n : Nat} -> Foldable (IArray n) where
273 | toList = ontoList [] n
277 | {n : Nat} -> Functor (IArray n) where
278 | map f arr = generate n (f . at arr)
281 | {n : Nat} -> Applicative (IArray n) where
283 | af <*> av = generate n (\x => at af x (at av x))
286 | {n : Nat} -> Monad (IArray n) where
287 | arr >>= f = generate n (\x => at (f $
at arr x) x)
290 | {n : Nat} -> Show a => Show (IArray n a) where
291 | showPrec p arr = showCon p "array" (showArg $
ontoList [] n arr)
295 | mapWithIndex : {n : _} -> (Fin n -> a -> b) -> IArray n a -> IArray n b
296 | mapWithIndex f arr = generate n (\x => f x (at arr x))
303 | updateAt : {n : _} -> Fin n -> (a -> a) -> IArray n a -> IArray n a
304 | updateAt x f = mapWithIndex (\k,v => if x == k then f v else v)
310 | setAt : {n : _} -> Fin n -> a -> IArray n a -> IArray n a
311 | setAt x y = mapWithIndex (\k,v => if x == k then y else v)
320 | traverseWithIndex :
322 | -> {auto app : Applicative f}
323 | -> (Fin n -> a -> f b)
326 | traverseWithIndex f arr =
327 | array <$> traverse (\(x,v) => f x v) (toVectWithIndex arr)
330 | {n : _} -> Traversable (IArray n) where
331 | traverse = traverseWithIndex . const
337 | 0 curLTE : (s : Ix m n) -> LTE c (ixToNat s) -> LTE c n
338 | curLTE s lte = transitive lte $
ixLTE s
340 | 0 curLT : (s : Ix (S m) n) -> LTE c (ixToNat s) -> LT c n
341 | curLT s lte = let LTESucc p := ixLT s in LTESucc $
transitive lte p
345 | drop : {n : _} -> (m : Nat) -> IArray n a -> IArray (n `minus` m) a
346 | drop m arr = generate (n `minus` m) (\f => at arr (inc f))
353 | -> (Fin n -> a -> Bool)
356 | filterWithKey f arr = run1 $ T1.do
357 | (
n ** m)
<- mfilterWithKey (unsafeThaw arr) f
358 | res <- unsafeFreeze m
363 | filter : {n : Nat} -> (a -> Bool) -> IArray n a -> Array a
364 | filter = filterWithKey . const
371 | -> (Fin n -> a -> Maybe b)
374 | mapMaybeWithKey f arr = run1 $ T1.do
375 | (
n ** m)
<- mmapMaybeWithKey (unsafeThaw arr) f
376 | res <- unsafeFreeze m
382 | mapMaybe : {n : Nat} -> (a -> Maybe b) -> IArray n a -> Array b
383 | mapMaybe = mapMaybeWithKey . const
394 | SnocSize : SnocList (Array a) -> Nat
396 | SnocSize (xs :< A s _) = SnocSize xs + s
400 | ListSize : List (Array a) -> Nat
401 | ListSize = SnocSize . ([<] <><)
407 | -> (x : IArray m a)
408 | -> (arrs : SnocList (Array a))
409 | -> {auto 0 lte1 : LTE pos n}
410 | -> {auto 0 lte2 : LTE cur m}
411 | -> WithMArray n a (IArray n a)
412 | sconc pos 0 _ (sx :< A s x) r t = sconc pos s x sx r t
413 | sconc (S j) (S k) x sx r t =
414 | let _ # t := setNat r j (atNat x k) t
415 | in sconc j k x sx r t
416 | sconc _ _ _ _ r t = unsafeFreeze r t
423 | snocConcat : (sa : SnocList (Array a)) -> IArray (SnocSize sa) a
424 | snocConcat [<] = empty
425 | snocConcat (sa :< A 0 _) =
426 | rewrite plusZeroRightNeutral (SnocSize sa) in snocConcat sa
427 | snocConcat (sa :< A (S k) arr) with (SnocSize sa + S k)
428 | _ | n = alloc n (at arr 0) (sconc n (S k) arr sa)
435 | listConcat : (as : List (Array a)) -> IArray (ListSize as) a
436 | listConcat as = snocConcat ([<] <>< as)
440 | append : {m,n : Nat} -> IArray m a -> IArray n a -> IArray (m + n) a
442 | unsafeAlloc (m+n) $
\r,t =>
443 | let _ # t := icopy {n = m+n} src1 0 0 m @{reflexive} @{lteAddRight _} r t
444 | _ # t := icopy src2 0 m n @{reflexive} @{reflexive} r t
445 | in unsafeFreeze r t
451 | parameters (arr : IArray n e)
453 | foldl1A : (k : Nat) -> Ix k n => (a -> e -> F1 s a) -> a -> F1 s a
454 | foldl1A 0 f x t = x # t
455 | foldl1A (S k) f x t = let y # t := f x (arr `ix` k) t in foldl1A k f y t
457 | foldr1A : (k : Nat) -> (0 p : LTE k n) => (e -> a -> F1 s a) -> a -> F1 s a
458 | foldr1A 0 f x t = x # t
459 | foldr1A (S k) f x t = let y # t := f (arr `atNat` k) x t in foldr1A k f y t
461 | fm1A : Semigroup a => (k : Nat) -> (0 p : LTE k n) => (e -> F1 s a) -> a -> F1 s a
462 | fm1A 0 f x t = x # t
463 | fm1A (S k) f x t = let y # t := f (arr `atNat` k) t in fm1A k f (y<+>x) t
465 | tr1A_ : (k : Nat) -> Ix k n => (e -> F1' s) -> F1' s
466 | tr1A_ 0 f t = () # t
467 | tr1A_ (S k) f t = let _ # t := f (arr `ix` k) t in tr1A_ k f t
469 | tr1A : (k : Nat) -> Ix k n => (e -> F1 s b) -> MArray s n b -> F1 s (IArray n b)
470 | tr1A 0 f m t = unsafeFreeze m t
472 | let y # t := f (arr `ix` k) t
473 | _ # t := setIx m k y t
478 | traverseKV1_ : {n : _} -> (Fin n -> a -> F1' q) -> IArray n a -> F1' q
479 | traverseKV1_ f arr = go n
481 | go : (k : Nat) -> (x : Ix k n) => F1' q
483 | go (S k) t = let _ # t := f (ixToFin x) (arr `ix` k) t in go k t
486 | {n : _} -> Foldable1 (IArray n) where
487 | foldl1 f x arr = foldl1A arr n f x
488 | foldr1 f x arr = foldr1A arr n f x
489 | foldMap1 f arr = fm1A arr n f neutral
490 | traverse1_ f arr = tr1A_ arr n f
493 | {n : _} -> Traversable1 (IArray n) where
494 | traverse1 f arr = unsafeMArray1 n >>= tr1A arr n f
497 | Foldable1 Array where
498 | foldl1 f x (A n arr) = foldl1A arr n f x
499 | foldr1 f x (A n arr) = foldr1A arr n f x
500 | foldMap1 f (A n arr) = fm1A arr n f neutral
501 | traverse1_ f (A n arr) = tr1A_ arr n f
504 | Traversable1 Array where
505 | traverse1 f (A n arr) t = let a # t := traverse1 f arr t in A n a # t