@@ -125,11 +125,15 @@ import Prelude hiding (iterate, replicate, repeat)
125125
126126-- $setup
127127-- >>> :m
128+-- >>> import Data.Function ((&))
128129-- >>> import Prelude hiding (iterate, replicate, repeat)
129130-- >>> import qualified Streamly.Prelude as Stream
130131-- >>> import qualified Streamly.Internal.Data.Stream.IsStream as Stream
131132-- >>> import qualified Streamly.Internal.Data.Unfold as Unfold
132133-- >>> import Control.Concurrent (threadDelay)
134+-- >>> import System.IO (stdout, hSetBuffering, BufferMode(LineBuffering))
135+--
136+-- >>> hSetBuffering stdout LineBuffering
133137
134138------------------------------------------------------------------------------
135139-- From Unfold
@@ -159,29 +163,26 @@ unfold0 unf = unfold unf (error "unfold0: unexpected void evaluation")
159163------------------------------------------------------------------------------
160164
161165-- |
162−-- @
166+-- >>> :{
163167-- unfoldr step s =
164168-- case step s of
165−-- Nothing -> 'K.nil'
166−-- Just (a, b) -> a \`cons` unfoldr step b
167−-- @
169+-- Nothing -> Stream.nil
170+-- Just (a, b) -> a `Stream.cons` unfoldr step b
171+-- :}
168172--
169173-- Build a stream by unfolding a /pure/ step function @step@ starting from a
170174-- seed @s@. The step function returns the next element in the stream and the
171175-- next seed value. When it is done it returns 'Nothing' and the stream ends.
172176-- For example,
173177--
174−-- @
175178-- >>> :{
176179-- let f b =
177−-- if b > 3
180+-- if b > 2
178181-- then Nothing
179182-- else Just (b, b + 1)
180183-- in Stream.toList $ Stream.unfoldr f 0
181184-- :}
182−-- [0,1,2,3]
183−--
184−-- @
185+-- [0,1,2]
185186--
186187-- @since 0.1.0
187188{-# INLINE_EARLY unfoldr #-}
@@ -195,26 +196,28 @@ unfoldr step seed = fromStreamS (S.unfoldr step seed)
195196-- seed value. When it is done it returns 'Nothing' and the stream ends. For
196197-- example,
197198--
198−-- @
199199-- >>> :{
200200-- let f b =
201−-- if b > 3
201+-- if b > 2
202202-- then return Nothing
203203-- else return (Just (b, b + 1))
204204-- in Stream.toList $ Stream.unfoldrM f 0
205205-- :}
206−-- [0,1,2,3]
206+-- [0,1,2]
207207--
208−-- @
209208-- When run concurrently, the next unfold step can run concurrently with the
210209-- processing of the output of the previous step. Note that more than one step
211210-- cannot run concurrently as the next step depends on the output of the
212211-- previous step.
213212--
214−-- @
215−-- (fromAsync $ S.unfoldrM (\\n -> liftIO (threadDelay 1000000) >> return (Just (n, n + 1))) 0)
216−-- & S.foldlM' (\\_ a -> threadDelay 1000000 >> print a) ()
217−-- @
213+-- >>> :{
214+-- let f b =
215+-- if b > 2
216+-- then return Nothing
217+-- else threadDelay 1000000 >> return (Just (b, b + 1))
218+-- in Stream.toList $ Stream.delay 1 $ Stream.fromAsync $ Stream.unfoldrM f 0
219+-- :}
220+-- [0,1,2]
218221--
219222-- /Concurrent/
220223--
@@ -253,9 +256,7 @@ repeat :: (IsStream t, Monad m) => a -> t m a
253256repeat = fromStreamS . S.repeat
254257
255258-- |
256−-- @
257−-- replicate = take n . repeat
258−-- @
259+-- >>> replicate n = Stream.take n . Stream.repeat
259260--
260261-- Generate a stream of length @n@ by repeating a value @n@ times.
261262--
@@ -265,16 +266,25 @@ replicate :: (IsStream t, Monad m) => Int -> a -> t m a
265266replicate n = fromStreamS . S.replicate n
266267
267268-- |
268−-- @
269−-- replicateM = take n . repeatM
270−-- @
269+-- >>> replicateM n = Stream.take n . Stream.repeatM
271270--
272271-- Generate a stream by performing a monadic action @n@ times. Same as:
273272--
274−-- @
275−-- drain $ fromSerial $ S.replicateM 10 $ (threadDelay 1000000 >> print 1)
276−-- drain $ fromAsync $ S.replicateM 10 $ (threadDelay 1000000 >> print 1)
277−-- @
273+-- >>> pr n = threadDelay 1000000 >> print n
274+--
275+-- This runs serially and takes 3 seconds:
276+--
277+-- >>> Stream.drain $ Stream.fromSerial $ Stream.replicateM 3 $ pr 1
278+-- 1
279+-- 1
280+-- 1
281+--
282+-- This runs concurrently and takes just 1 second:
283+--
284+-- >>> Stream.drain $ Stream.fromAsync $ Stream.replicateM 3 $ pr 1
285+-- 1
286+-- 1
287+-- 1
278288--
279289-- /Concurrent/
280290--
@@ -398,10 +408,8 @@ timeout = undefined
398408-- map. Check performance equivalence.
399409--
400410-- |
401−-- @
402−-- fromIndices f = fmap f $ Stream.enumerateFrom 0
403−-- fromIndices f = let g i = f i \`cons` g (i + 1) in g 0
404−-- @
411+-- >>> fromIndices f = fmap f $ Stream.enumerateFrom 0
412+-- >>> fromIndices f = let g i = f i `Stream.cons` g (i + 1) in g 0
405413--
406414-- Generate an infinite stream, whose values are the output of a function @f@
407415-- applied on the corresponding index. Index starts at 0.
@@ -416,10 +424,8 @@ fromIndices = fromStreamS . S.fromIndices
416424
417425--
418426-- |
419−-- @
420−-- fromIndicesM f = Stream.mapM f $ Stream.enumerateFrom 0
421−-- fromIndicesM f = let g i = f i \`consM` g (i + 1) in g 0
422−-- @
427+-- >>> fromIndicesM f = Stream.mapM f $ Stream.enumerateFrom 0
428+-- >>> fromIndicesM f = let g i = f i `Stream.consM` g (i + 1) in g 0
423429--
424430-- Generate an infinite stream, whose values are the output of a monadic
425431-- function @f@ applied on the corresponding index. Index starts at 0.
@@ -442,46 +448,54 @@ fromIndicesMSerial = fromStreamS . S.fromIndicesM
442448------------------------------------------------------------------------------
443449
444450-- |
445−-- @
446−-- iterate f x = x \`cons` iterate f x
447−-- @
451+-- >>> iterate f x = x `Stream.cons` iterate f x
448452--
449453-- Generate an infinite stream with @x@ as the first element and each
450454-- successive element derived by applying the function @f@ on the previous
451455-- element.
452456--
453−-- @
454457-- >>> Stream.toList $ Stream.take 5 $ Stream.iterate (+1) 1
455458-- [1,2,3,4,5]
456459--
457−-- @
458−--
459460-- @since 0.1.2
460461{-# INLINE_NORMAL iterate #-}
461462iterate :: (IsStream t, Monad m) => (a -> a) -> a -> t m a
462463iterate step = fromStreamS . S.iterate step
463464
464465-- |
465−-- @
466−-- iterateM f m = m >>= \a -> return a \`consM` iterateM f (f a)
467−-- @
466+-- >>> iterateM f m = m >>= \a -> return a `Stream.consM` iterateM f (f a)
468467--
469468-- Generate an infinite stream with the first element generated by the action
470469-- @m@ and each successive element derived by applying the monadic function
471470-- @f@ on the previous element.
472471--
472+-- >>> pr n = threadDelay 1000000 >> print n
473+-- >>> :{
474+-- Stream.iterateM (\x -> pr x >> return (x + 1)) (return 0)
475+-- & Stream.take 3
476+-- & Stream.fromSerial
477+-- & Stream.toList
478+-- :}
479+-- 0
480+-- 1
481+-- [0,1,2]
482+--
473483-- When run concurrently, the next iteration can run concurrently with the
474484-- processing of the previous iteration. Note that more than one iteration
475485-- cannot run concurrently as the next iteration depends on the output of the
476486-- previous iteration.
477487--
478−-- @
479−-- drain $ fromSerial $ S.take 10 $ S.iterateM
480−-- (\\x -> threadDelay 1000000 >> print x >> return (x + 1)) (return 0)
481−--
482−-- drain $ fromAsync $ S.take 10 $ S.iterateM
483−-- (\\x -> threadDelay 1000000 >> print x >> return (x + 1)) (return 0)
484−-- @
488+-- >>> :{
489+-- Stream.iterateM (\x -> pr x >> return (x + 1)) (return 0)
490+-- & Stream.delay 1
491+-- & Stream.take 3
492+-- & Stream.fromAsync
493+-- & Stream.toList
494+-- :}
495+-- 0
496+-- 1
497+-- 2
498+-- [0,1,2]
485499--
486500-- /Concurrent/
487501--
@@ -505,13 +519,12 @@ iterateMSerial step = fromStreamS . S.iterateM step
505519--
506520-- The function @fix@ defined as:
507521--
508−-- > fix f = let x = f x in x
522+-- >>> fix f = let x = f x in x
509523--
510524-- ensures that the argument of a function and its output refer to the same
511525-- lazy value @x@ i.e. the same location in memory. Thus @x@ can be defined
512526-- in terms of itself, creating structures with cyclic references.
513527--
514−-- >>> import Data.Function (fix)
515528-- >>> f ~(a, b) = ([1, b], head a)
516529-- >>> fix f
517530-- ([1,1],1)
@@ -529,21 +542,18 @@ iterateMSerial step = fromStreamS . S.iterateM step
529542-- represents the tuple @(x,y)@ returned by it in a given iteration. We define
530543-- the first element of the tuple in terms of the second.
531544--
532−-- @
533−-- import Streamly.Internal.Data.Stream.IsStream as Stream
534−-- import System.IO.Unsafe (unsafeInterleaveIO)
535−--
536−-- main = do
537−-- Stream.mapM_ print $ Stream.mfix f
545+-- >>> import Streamly.Internal.Data.Stream.IsStream as Stream
546+-- >>> import System.IO.Unsafe (unsafeInterleaveIO)
538547--
548+-- >>> :{
549+-- main = Stream.mapM_ print $ Stream.mfix f
539550-- where
540−--
541551-- f action = do
542552-- let incr n act = fmap ((+n) . snd) $ unsafeInterleaveIO act
543553-- x <- Stream.fromListM [incr 1 action, incr 2 action]
544554-- y <- Stream.fromList [4,5]
545555-- return (x, y)
546−-- @
556+-- :}
547557--
548558-- Note: you cannot achieve this by just changing the order of the monad
549559-- statements because that would change the order in which the stream elements
@@ -562,9 +572,7 @@ mfix f = fromStream $ K.mfix (toStream . f)
562572------------------------------------------------------------------------------
563573
564574-- |
565−-- @
566−-- fromFoldable = 'Prelude.foldr' 'cons' 'nil'
567−-- @
575+-- >>> fromFoldable = Prelude.foldr Stream.cons Stream.nil
568576--
569577-- Construct a stream from a 'Foldable' containing pure values:
570578--
@@ -574,16 +582,20 @@ fromFoldable :: (IsStream t, Foldable f) => f a -> t m a
574582fromFoldable = fromStream . K.fromFoldable
575583
576584-- |
577−-- @
578−-- fromFoldableM = 'Prelude.foldr' 'consM' 'K.nil'
579−-- @
585+-- >>> fromFoldableM = Prelude.foldr Stream.consM Stream.nil
580586--
581587-- Construct a stream from a 'Foldable' containing monadic actions.
582588--
583−-- @
584−-- drain $ fromSerial $ S.fromFoldableM $ replicateM 10 (threadDelay 1000000 >> print 1)
585−-- drain $ fromAsync $ S.fromFoldableM $ replicateM 10 (threadDelay 1000000 >> print 1)
586−-- @
589+-- >>> pr n = threadDelay 1000000 >> print n
590+-- >>> Stream.drain $ Stream.fromSerial $ Stream.fromFoldableM $ map pr [1,2,3]
591+-- 1
592+-- 2
593+-- 3
594+--
595+-- >>> Stream.drain $ Stream.fromAsync $ Stream.fromFoldableM $ map pr [1,2,3]
596+-- ...
597+-- ...
598+-- ...
587599--
588600-- /Concurrent (do not use with 'fromParallel' on infinite containers)/
589601--
@@ -593,9 +605,10 @@ fromFoldableM :: (IsStream t, MonadAsync m, Foldable f) => f (m a) -> t m a
593605fromFoldableM = Prelude.foldr consM IsStream.nil
594606
595607-- |
596−-- @
597−-- fromListM = 'Prelude.foldr' 'K.consM' 'K.nil'
598−-- @
608+-- >>> fromListM = Stream.fromFoldableM
609+-- >>> fromListM = Stream.sequence . Stream.fromList
610+-- >>> fromListM = Stream.mapM id . Stream.fromList
611+-- >>> fromListM = Prelude.foldr Stream.consM Stream.nil
599612--
600613-- Construct a stream from a list of monadic actions. This is more efficient
601614-- than 'fromFoldableM' for serial streams.