Replace basicNew by unsafeFreeze
[darcs-mirrors/vector.git] / Data / Vector / Generic.hs
1 {-# LANGUAGE Rank2Types, MultiParamTypeClasses, FlexibleContexts,
2 TypeFamilies, ScopedTypeVariables #-}
3 -- |
4 -- Module : Data.Vector.Generic
5 -- Copyright : (c) Roman Leshchinskiy 2008-2009
6 -- License : BSD-style
7 --
8 -- Maintainer : Roman Leshchinskiy <rl@cse.unsw.edu.au>
9 -- Stability : experimental
10 -- Portability : non-portable
11 --
12 -- Generic interface to pure vectors
13 --
14
15 module Data.Vector.Generic (
16 -- * Immutable vectors
17 Vector(..), Mutable,
18
19 -- * Length information
20 length, null,
21
22 -- * Construction
23 empty, singleton, cons, snoc, replicate, (++), copy,
24
25 -- * Accessing individual elements
26 (!), head, last, indexM, headM, lastM,
27 unsafeIndex, unsafeIndexM,
28
29 -- * Subvectors
30 slice, init, tail, take, drop,
31 unsafeSlice,
32
33 -- * Permutations
34 accum, accumulate, accumulate_,
35 (//), update, update_,
36 backpermute, reverse,
37
38 -- * Mapping
39 map, concatMap,
40
41 -- * Zipping and unzipping
42 zipWith, zipWith3, zip, zip3, unzip, unzip3,
43
44 -- * Comparisons
45 eq, cmp,
46
47 -- * Filtering
48 filter, takeWhile, dropWhile,
49
50 -- * Searching
51 elem, notElem, find, findIndex,
52
53 -- * Folding
54 foldl, foldl1, foldl', foldl1', foldr, foldr1,
55
56 -- * Specialised folds
57 and, or, sum, product, maximum, minimum,
58
59 -- * Unfolding
60 unfoldr,
61
62 -- * Scans
63 prescanl, prescanl',
64 postscanl, postscanl',
65 scanl, scanl', scanl1, scanl1',
66
67 -- * Enumeration
68 enumFromTo, enumFromThenTo,
69
70 -- * Conversion to/from lists
71 toList, fromList,
72
73 -- * Conversion to/from Streams
74 stream, unstream,
75
76 -- * MVector-based initialisation
77 new
78 ) where
79
80 import Data.Vector.Generic.Mutable ( MVector )
81
82 import qualified Data.Vector.Generic.New as New
83 import Data.Vector.Generic.New ( New )
84
85 import qualified Data.Vector.Fusion.Stream as Stream
86 import Data.Vector.Fusion.Stream ( Stream, MStream, inplace, inplace' )
87 import qualified Data.Vector.Fusion.Stream.Monadic as MStream
88 import Data.Vector.Fusion.Stream.Size
89 import Data.Vector.Fusion.Util
90
91 import Control.Monad.ST ( runST )
92 import Control.Monad.Primitive
93 import Prelude hiding ( length, null,
94 replicate, (++),
95 head, last,
96 init, tail, take, drop, reverse,
97 map, concatMap,
98 zipWith, zipWith3, zip, zip3, unzip, unzip3,
99 filter, takeWhile, dropWhile,
100 elem, notElem,
101 foldl, foldl1, foldr, foldr1,
102 and, or, sum, product, maximum, minimum,
103 scanl, scanl1,
104 enumFromTo, enumFromThenTo )
105
106 #include "vector.h"
107
108 type family Mutable (v :: * -> *) :: * -> * -> *
109
110 -- | Class of immutable vectors.
111 --
112 class MVector (Mutable v) a => Vector v a where
113 -- | Unsafely convert a mutable vector to its immutable version
114 -- without copying. The mutable vector may not be used after
115 -- this operation.
116 unsafeFreeze :: PrimMonad m => Mutable v (PrimState m) a -> m (v a)
117
118 -- | Length of the vector (not fusible!)
119 basicLength :: v a -> Int
120
121 -- | Yield a part of the vector without copying it. No range checks!
122 basicUnsafeSlice :: v a -> Int -> Int -> v a
123
124 -- | Yield the element at the given position in a monad. The monad allows us
125 -- to be strict in the vector if we want. Suppose we had
126 --
127 -- > unsafeIndex :: v a -> Int -> a
128 --
129 -- instead. Now, if we wanted to copy a vector, we'd do something like
130 --
131 -- > copy mv v ... = ... unsafeWrite mv i (unsafeIndex v i) ...
132 --
133 -- For lazy vectors, the indexing would not be evaluated which means that we
134 -- would retain a reference to the original vector in each element we write.
135 -- This is not what we want!
136 --
137 -- With 'basicUnsafeIndexM', we can do
138 --
139 -- > copy mv v ... = ... case basicUnsafeIndexM v i of
140 -- > Box x -> unsafeWrite mv i x ...
141 --
142 -- which does not have this problem because indexing (but not the returned
143 -- element!) is evaluated immediately.
144 --
145 basicUnsafeIndexM :: Monad m => v a -> Int -> m a
146
147 -- Fusion
148 -- ------
149
150 -- | Construct a pure vector from a monadic initialiser
151 new :: Vector v a => New a -> v a
152 {-# INLINE new #-}
153 new m = new' undefined m
154
155 -- | Same as 'new' but with a dummy argument necessary for correctly typing
156 -- the rule @uninplace@.
157 --
158 -- See http://hackage.haskell.org/trac/ghc/ticket/2600
159 new' :: Vector v a => v a -> New a -> v a
160 {-# INLINE_STREAM new' #-}
161 new' _ m = runST (do
162 mv <- New.run m
163 unsafeFreeze mv)
164
165 -- | Convert a vector to a 'Stream'
166 stream :: Vector v a => v a -> Stream a
167 {-# INLINE_STREAM stream #-}
168 stream v = v `seq` (Stream.unfoldr get 0 `Stream.sized` Exact n)
169 where
170 n = length v
171
172 -- NOTE: the False case comes first in Core so making it the recursive one
173 -- makes the code easier to read
174 {-# INLINE get #-}
175 get i | i >= n = Nothing
176 | otherwise = case basicUnsafeIndexM v i of Box x -> Just (x, i+1)
177
178 -- | Create a vector from a 'Stream'
179 unstream :: Vector v a => Stream a -> v a
180 {-# INLINE unstream #-}
181 unstream s = new (New.unstream s)
182
183 {-# RULES
184
185 "stream/unstream [Vector]" forall v s.
186 stream (new' v (New.unstream s)) = s
187
188 "New.unstream/stream/new [Vector]" forall v p.
189 New.unstream (stream (new' v p)) = p
190
191 #-}
192
193 {-# RULES
194
195 "inplace [Vector]"
196 forall (f :: forall m. Monad m => MStream m a -> MStream m a) v m.
197 New.unstream (inplace f (stream (new' v m))) = New.transform f m
198
199 "uninplace [Vector]"
200 forall (f :: forall m. Monad m => MStream m a -> MStream m a) v m.
201 stream (new' v (New.transform f m)) = inplace f (stream (new' v m))
202
203 #-}
204
205 -- Length
206 -- ------
207
208 length :: Vector v a => v a -> Int
209 {-# INLINE_STREAM length #-}
210 length v = basicLength v
211
212 {-# RULES
213
214 "length/unstream [Vector]" forall v s.
215 length (new' v (New.unstream s)) = Stream.length s
216
217 #-}
218
219 null :: Vector v a => v a -> Bool
220 {-# INLINE null #-}
221 null v = length v == 0
222
223 -- Construction
224 -- ------------
225
226 -- | Empty vector
227 empty :: Vector v a => v a
228 {-# INLINE empty #-}
229 empty = unstream Stream.empty
230
231 -- | Vector with exaclty one element
232 singleton :: Vector v a => a -> v a
233 {-# INLINE singleton #-}
234 singleton x = unstream (Stream.singleton x)
235
236 -- | Vector of the given length with the given value in each position
237 replicate :: Vector v a => Int -> a -> v a
238 {-# INLINE replicate #-}
239 replicate n = unstream . Stream.replicate n
240
241 -- | Prepend an element
242 cons :: Vector v a => a -> v a -> v a
243 {-# INLINE cons #-}
244 cons x = unstream . Stream.cons x . stream
245
246 -- | Append an element
247 snoc :: Vector v a => v a -> a -> v a
248 {-# INLINE snoc #-}
249 snoc v = unstream . Stream.snoc (stream v)
250
251 infixr 5 ++
252 -- | Concatenate two vectors
253 (++) :: Vector v a => v a -> v a -> v a
254 {-# INLINE (++) #-}
255 v ++ w = unstream (stream v Stream.++ stream w)
256
257 -- | Create a copy of a vector. Useful when dealing with slices.
258 copy :: Vector v a => v a -> v a
259 {-# INLINE_STREAM copy #-}
260 copy = unstream . stream
261
262 {-# RULES
263
264 "copy/unstream [Vector]" forall v s.
265 copy (new' v (New.unstream s)) = new' v (New.unstream s)
266
267 #-}
268
269 -- Accessing individual elements
270 -- -----------------------------
271
272 -- | Indexing
273 (!) :: Vector v a => v a -> Int -> a
274 {-# INLINE_STREAM (!) #-}
275 v ! i = BOUNDS_CHECK(checkIndex) "(!)" i (length v)
276 $ unId (basicUnsafeIndexM v i)
277
278 -- | Unsafe indexing without bounds checking
279 unsafeIndex :: Vector v a => v a -> Int -> a
280 {-# INLINE_STREAM unsafeIndex #-}
281 unsafeIndex v i = UNSAFE_CHECK(checkIndex) "unsafeIndex" i (length v)
282 $ unId (basicUnsafeIndexM v i)
283
284 -- | First element
285 head :: Vector v a => v a -> a
286 {-# INLINE_STREAM head #-}
287 head v = v ! 0
288
289 -- | Last element
290 last :: Vector v a => v a -> a
291 {-# INLINE_STREAM last #-}
292 last v = v ! (length v - 1)
293
294 {-# RULES
295
296 "(!)/unstream [Vector]" forall v i s.
297 new' v (New.unstream s) ! i = s Stream.!! i
298
299 "unsafeIndex/unstream [Vector]" forall v i s.
300 unsafeIndex (new' v (New.unstream s)) i = s Stream.!! i
301
302 "head/unstream [Vector]" forall v s.
303 head (new' v (New.unstream s)) = Stream.head s
304
305 "last/unstream [Vector]" forall v s.
306 last (new' v (New.unstream s)) = Stream.last s
307
308 #-}
309
310 -- | Monadic indexing which can be strict in the vector while remaining lazy in
311 -- the element.
312 indexM :: (Vector v a, Monad m) => v a -> Int -> m a
313 {-# INLINE_STREAM indexM #-}
314 indexM v i = BOUNDS_CHECK(checkIndex) "indexM" i (length v)
315 $ basicUnsafeIndexM v i
316
317 -- | Unsafe monadic indexing without bounds checks
318 unsafeIndexM :: (Vector v a, Monad m) => v a -> Int -> m a
319 {-# INLINE_STREAM unsafeIndexM #-}
320 unsafeIndexM v i = UNSAFE_CHECK(checkIndex) "unsafeIndexM" i (length v)
321 $ basicUnsafeIndexM v i
322
323 headM :: (Vector v a, Monad m) => v a -> m a
324 {-# INLINE_STREAM headM #-}
325 headM v = indexM v 0
326
327 lastM :: (Vector v a, Monad m) => v a -> m a
328 {-# INLINE_STREAM lastM #-}
329 lastM v = indexM v (length v - 1)
330
331 -- FIXME: the rhs of these rules are lazy in the stream which is WRONG
332 {- RULES
333
334 "indexM/unstream [Vector]" forall v i s.
335 indexM (new' v (New.unstream s)) i = return (s Stream.!! i)
336
337 "headM/unstream [Vector]" forall v s.
338 headM (new' v (New.unstream s)) = return (Stream.head s)
339
340 "lastM/unstream [Vector]" forall v s.
341 lastM (new' v (New.unstream s)) = return (Stream.last s)
342
343 -}
344
345 -- Subarrays
346 -- ---------
347
348 -- FIXME: slicing doesn't work with the inplace stuff at the moment
349
350 -- | Yield a part of the vector without copying it.
351 slice :: Vector v a => v a -> Int -- ^ starting index
352 -> Int -- ^ length
353 -> v a
354 {-# INLINE_STREAM slice #-}
355 slice v i n = BOUNDS_CHECK(checkSlice) "slice" i n (length v)
356 $ basicUnsafeSlice v i n
357
358 -- | Unsafely yield a part of the vector without copying it and without
359 -- performing bounds checks.
360 unsafeSlice :: Vector v a => v a -> Int -- ^ starting index
361 -> Int -- ^ length
362 -> v a
363 {-# INLINE_STREAM unsafeSlice #-}
364 unsafeSlice v i n = UNSAFE_CHECK(checkSlice) "unsafeSlice" i n (length v)
365 $ basicUnsafeSlice v i n
366
367 -- | Yield all but the last element without copying.
368 init :: Vector v a => v a -> v a
369 {-# INLINE_STREAM init #-}
370 init v = slice v 0 (length v - 1)
371
372 -- | All but the first element (without copying).
373 tail :: Vector v a => v a -> v a
374 {-# INLINE_STREAM tail #-}
375 tail v = slice v 1 (length v - 1)
376
377 -- | Yield the first @n@ elements without copying.
378 take :: Vector v a => Int -> v a -> v a
379 {-# INLINE_STREAM take #-}
380 take n v = slice v 0 (min n' (length v))
381 where n' = max n 0
382
383 -- | Yield all but the first @n@ elements without copying.
384 drop :: Vector v a => Int -> v a -> v a
385 {-# INLINE_STREAM drop #-}
386 drop n v = slice v (min n' len) (max 0 (len - n'))
387 where n' = max n 0
388 len = length v
389
390 {-# RULES
391
392 "slice/new [Vector]" forall v p i n.
393 slice (new' v p) i n = new' v (New.slice p i n)
394
395 "unsafeSlice/new [Vector]" forall v p i n.
396 unsafeSlice (new' v p) i n = new' v (New.unsafeSlice p i n)
397
398 "init/new [Vector]" forall v p.
399 init (new' v p) = new' v (New.init p)
400
401 "tail/new [Vector]" forall v p.
402 tail (new' v p) = new' v (New.tail p)
403
404 "take/new [Vector]" forall n v p.
405 take n (new' v p) = new' v (New.take n p)
406
407 "drop/new [Vector]" forall n v p.
408 drop n (new' v p) = new' v (New.drop n p)
409
410 #-}
411
412 -- Permutations
413 -- ------------
414
415 accum_stream :: Vector v a => (a -> b -> a) -> v a -> Stream (Int,b) -> v a
416 {-# INLINE accum_stream #-}
417 accum_stream f v s = new (New.accum f (New.unstream (stream v)) s)
418
419 accum :: Vector v a => (a -> b -> a) -> v a -> [(Int,b)] -> v a
420 {-# INLINE accum #-}
421 accum f v us = accum_stream f v (Stream.fromList us)
422
423 accumulate :: (Vector v a, Vector v (Int, b))
424 => (a -> b -> a) -> v a -> v (Int,b) -> v a
425 {-# INLINE accumulate #-}
426 accumulate f v us = accum_stream f v (stream us)
427
428 accumulate_ :: (Vector v a, Vector v Int, Vector v b)
429 => (a -> b -> a) -> v a -> v Int -> v b -> v a
430 {-# INLINE accumulate_ #-}
431 accumulate_ f v is xs = accum_stream f v (Stream.zipWith (,) (stream is)
432 (stream xs))
433
434
435 update_stream :: Vector v a => v a -> Stream (Int,a) -> v a
436 {-# INLINE update_stream #-}
437 update_stream v s = new (New.update (New.unstream (stream v)) s)
438
439 (//) :: Vector v a => v a -> [(Int, a)] -> v a
440 {-# INLINE (//) #-}
441 v // us = update_stream v (Stream.fromList us)
442
443 update :: (Vector v a, Vector v (Int, a)) => v a -> v (Int, a) -> v a
444 {-# INLINE update #-}
445 update v w = update_stream v (stream w)
446
447 update_ :: (Vector v a, Vector v Int) => v a -> v Int -> v a -> v a
448 {-# INLINE update_ #-}
449 update_ v is w = update_stream v (Stream.zipWith (,) (stream is) (stream w))
450
451 -- This somewhat non-intuitive definition ensures that the resulting vector
452 -- does not retain references to the original one even if it is lazy in its
453 -- elements. This would not be the case if we simply used
454 --
455 -- backpermute v is = map (v!) is
456 backpermute :: (Vector v a, Vector v Int) => v a -> v Int -> v a
457 {-# INLINE backpermute #-}
458 backpermute v is = seq v
459 $ unstream
460 $ Stream.unbox
461 $ Stream.map (indexM v)
462 $ stream is
463
464 reverse :: (Vector v a) => v a -> v a
465 {-# INLINE reverse #-}
466 reverse = new . New.reverse . New.unstream . stream
467
468 -- Mapping
469 -- -------
470
471 -- | Map a function over a vector
472 map :: (Vector v a, Vector v b) => (a -> b) -> v a -> v b
473 {-# INLINE map #-}
474 map f = unstream . inplace' (MStream.map f) . stream
475
476 concatMap :: (Vector v a, Vector v b) => (a -> v b) -> v a -> v b
477 {-# INLINE concatMap #-}
478 concatMap f = unstream . Stream.concatMap (stream . f) . stream
479
480 -- Zipping/unzipping
481 -- -----------------
482
483 -- | Zip two vectors with the given function.
484 zipWith :: (Vector v a, Vector v b, Vector v c) => (a -> b -> c) -> v a -> v b -> v c
485 {-# INLINE zipWith #-}
486 zipWith f xs ys = unstream (Stream.zipWith f (stream xs) (stream ys))
487
488 -- | Zip three vectors with the given function.
489 zipWith3 :: (Vector v a, Vector v b, Vector v c, Vector v d) => (a -> b -> c -> d) -> v a -> v b -> v c -> v d
490 {-# INLINE zipWith3 #-}
491 zipWith3 f xs ys zs = unstream (Stream.zipWith3 f (stream xs) (stream ys) (stream zs))
492
493 zip :: (Vector v a, Vector v b, Vector v (a,b)) => v a -> v b -> v (a, b)
494 {-# INLINE zip #-}
495 zip = zipWith (,)
496
497 zip3 :: (Vector v a, Vector v b, Vector v c, Vector v (a, b, c)) => v a -> v b -> v c -> v (a, b, c)
498 {-# INLINE zip3 #-}
499 zip3 = zipWith3 (,,)
500
501 unzip :: (Vector v a, Vector v b, Vector v (a,b)) => v (a, b) -> (v a, v b)
502 {-# INLINE unzip #-}
503 unzip xs = (map fst xs, map snd xs)
504
505 unzip3 :: (Vector v a, Vector v b, Vector v c, Vector v (a, b, c)) => v (a, b, c) -> (v a, v b, v c)
506 {-# INLINE unzip3 #-}
507 unzip3 xs = (map (\(a, b, c) -> a) xs, map (\(a, b, c) -> b) xs, map (\(a, b, c) -> c) xs)
508
509 -- Comparisons
510 -- -----------
511
512 eq :: (Vector v a, Eq a) => v a -> v a -> Bool
513 {-# INLINE eq #-}
514 xs `eq` ys = stream xs == stream ys
515
516 cmp :: (Vector v a, Ord a) => v a -> v a -> Ordering
517 {-# INLINE cmp #-}
518 cmp xs ys = compare (stream xs) (stream ys)
519
520 -- Filtering
521 -- ---------
522
523 -- | Drop elements which do not satisfy the predicate
524 filter :: Vector v a => (a -> Bool) -> v a -> v a
525 {-# INLINE filter #-}
526 filter f = unstream . inplace (MStream.filter f) . stream
527
528 -- | Yield the longest prefix of elements satisfying the predicate.
529 takeWhile :: Vector v a => (a -> Bool) -> v a -> v a
530 {-# INLINE takeWhile #-}
531 takeWhile f = unstream . Stream.takeWhile f . stream
532
533 -- | Drop the longest prefix of elements that satisfy the predicate.
534 dropWhile :: Vector v a => (a -> Bool) -> v a -> v a
535 {-# INLINE dropWhile #-}
536 dropWhile f = unstream . Stream.dropWhile f . stream
537
538 -- Searching
539 -- ---------
540
541 infix 4 `elem`
542 -- | Check whether the vector contains an element
543 elem :: (Vector v a, Eq a) => a -> v a -> Bool
544 {-# INLINE elem #-}
545 elem x = Stream.elem x . stream
546
547 infix 4 `notElem`
548 -- | Inverse of `elem`
549 notElem :: (Vector v a, Eq a) => a -> v a -> Bool
550 {-# INLINE notElem #-}
551 notElem x = Stream.notElem x . stream
552
553 -- | Yield 'Just' the first element matching the predicate or 'Nothing' if no
554 -- such element exists.
555 find :: Vector v a => (a -> Bool) -> v a -> Maybe a
556 {-# INLINE find #-}
557 find f = Stream.find f . stream
558
559 -- | Yield 'Just' the index of the first element matching the predicate or
560 -- 'Nothing' if no such element exists.
561 findIndex :: Vector v a => (a -> Bool) -> v a -> Maybe Int
562 {-# INLINE findIndex #-}
563 findIndex f = Stream.findIndex f . stream
564
565 -- Folding
566 -- -------
567
568 -- | Left fold
569 foldl :: Vector v b => (a -> b -> a) -> a -> v b -> a
570 {-# INLINE foldl #-}
571 foldl f z = Stream.foldl f z . stream
572
573 -- | Lefgt fold on non-empty vectors
574 foldl1 :: Vector v a => (a -> a -> a) -> v a -> a
575 {-# INLINE foldl1 #-}
576 foldl1 f = Stream.foldl1 f . stream
577
578 -- | Left fold with strict accumulator
579 foldl' :: Vector v b => (a -> b -> a) -> a -> v b -> a
580 {-# INLINE foldl' #-}
581 foldl' f z = Stream.foldl' f z . stream
582
583 -- | Left fold on non-empty vectors with strict accumulator
584 foldl1' :: Vector v a => (a -> a -> a) -> v a -> a
585 {-# INLINE foldl1' #-}
586 foldl1' f = Stream.foldl1' f . stream
587
588 -- | Right fold
589 foldr :: Vector v a => (a -> b -> b) -> b -> v a -> b
590 {-# INLINE foldr #-}
591 foldr f z = Stream.foldr f z . stream
592
593 -- | Right fold on non-empty vectors
594 foldr1 :: Vector v a => (a -> a -> a) -> v a -> a
595 {-# INLINE foldr1 #-}
596 foldr1 f = Stream.foldr1 f . stream
597
598 -- Specialised folds
599 -- -----------------
600
601 and :: Vector v Bool => v Bool -> Bool
602 {-# INLINE and #-}
603 and = Stream.and . stream
604
605 or :: Vector v Bool => v Bool -> Bool
606 {-# INLINE or #-}
607 or = Stream.or . stream
608
609 sum :: (Vector v a, Num a) => v a -> a
610 {-# INLINE sum #-}
611 sum = Stream.foldl' (+) 0 . stream
612
613 product :: (Vector v a, Num a) => v a -> a
614 {-# INLINE product #-}
615 product = Stream.foldl' (*) 1 . stream
616
617 maximum :: (Vector v a, Ord a) => v a -> a
618 {-# INLINE maximum #-}
619 maximum = Stream.foldl1' max . stream
620
621 minimum :: (Vector v a, Ord a) => v a -> a
622 {-# INLINE minimum #-}
623 minimum = Stream.foldl1' min . stream
624
625 -- Unfolding
626 -- ---------
627
628 unfoldr :: Vector v a => (b -> Maybe (a, b)) -> b -> v a
629 {-# INLINE unfoldr #-}
630 unfoldr f = unstream . Stream.unfoldr f
631
632 -- Scans
633 -- -----
634
635 -- | Prefix scan
636 prescanl :: (Vector v a, Vector v b) => (a -> b -> a) -> a -> v b -> v a
637 {-# INLINE prescanl #-}
638 prescanl f z = unstream . inplace' (MStream.prescanl f z) . stream
639
640 -- | Prefix scan with strict accumulator
641 prescanl' :: (Vector v a, Vector v b) => (a -> b -> a) -> a -> v b -> v a
642 {-# INLINE prescanl' #-}
643 prescanl' f z = unstream . inplace' (MStream.prescanl' f z) . stream
644
645 -- | Suffix scan
646 postscanl :: (Vector v a, Vector v b) => (a -> b -> a) -> a -> v b -> v a
647 {-# INLINE postscanl #-}
648 postscanl f z = unstream . inplace' (MStream.postscanl f z) . stream
649
650 -- | Suffix scan with strict accumulator
651 postscanl' :: (Vector v a, Vector v b) => (a -> b -> a) -> a -> v b -> v a
652 {-# INLINE postscanl' #-}
653 postscanl' f z = unstream . inplace' (MStream.postscanl' f z) . stream
654
655 -- | Haskell-style scan
656 scanl :: (Vector v a, Vector v b) => (a -> b -> a) -> a -> v b -> v a
657 {-# INLINE scanl #-}
658 scanl f z = unstream . Stream.scanl f z . stream
659
660 -- | Haskell-style scan with strict accumulator
661 scanl' :: (Vector v a, Vector v b) => (a -> b -> a) -> a -> v b -> v a
662 {-# INLINE scanl' #-}
663 scanl' f z = unstream . Stream.scanl' f z . stream
664
665 -- | Scan over a non-empty vector
666 scanl1 :: Vector v a => (a -> a -> a) -> v a -> v a
667 {-# INLINE scanl1 #-}
668 scanl1 f = unstream . inplace (MStream.scanl1 f) . stream
669
670 -- | Scan over a non-empty vector with a strict accumulator
671 scanl1' :: Vector v a => (a -> a -> a) -> v a -> v a
672 {-# INLINE scanl1' #-}
673 scanl1' f = unstream . inplace (MStream.scanl1' f) . stream
674
675 -- Enumeration
676 -- -----------
677
678 enumFromTo :: (Vector v a, Enum a) => a -> a -> v a
679 {-# INLINE enumFromTo #-}
680 enumFromTo x y = unstream (Stream.enumFromTo x y)
681
682 enumFromThenTo :: (Vector v a, Enum a) => a -> a -> a -> v a
683 {-# INLINE enumFromThenTo #-}
684 enumFromThenTo x y z = unstream (Stream.enumFromThenTo x y z)
685
686 -- | Convert a vector to a list
687 toList :: Vector v a => v a -> [a]
688 {-# INLINE toList #-}
689 toList = Stream.toList . stream
690
691 -- | Convert a list to a vector
692 fromList :: Vector v a => [a] -> v a
693 {-# INLINE fromList #-}
694 fromList = unstream . Stream.fromList
695