module Data.Stream.Monadic
( Step (..)
, Stream (..)
, toList
, fromList
, append
, cons
, snoc
, head
, last
, tail
, init
, null
, length
, map
, mapM
, mapM_
, reverse
, intersperse
, intercalate
, foldl
, foldl'
, foldr
, foldMap
, foldM
, foldM_
, concat
, concatMap
, and
, or
, any
, all
, sum
, product
, scanl
, iterate
, repeat
, replicate
, cycle
, unfoldr
, unfoldrM
, take
, drop
, splitAt
, takeWhile
, dropWhile
, span
, break
, isPrefixOf
, isSuffixOf
, elem
, notElem
, lookup
, find
, filter
, zip
, zip3
, zip4
, zipWith
, zipWith3
, zipWith4
, unzip
, unzip3
, unzip4
, delete
, insert
, deleteBy
, insertBy
, genericLength
, genericTake
, genericDrop
, genericSplitAt
, genericReplicate
, enumFromToInt
, enumFromToChar
, enumDeltaInteger
)
where
import Control.Applicative
import Control.Monad (Monad (..), void, (=<<), (>=>))
import Data.Char (Char, chr, ord)
import Data.Monoid
import Debug.Trace
import Prelude (Bool (..), Either (..), Eq (..), Functor (..), Int, Integer,
Integral (..), Maybe (..), Num (..), Ord (..), Ordering (..),
error, flip, not, otherwise, undefined, ($), (&&), (.), (||))
data Step a s
= Yield a !s
| Skip !s
| Done
data Stream m a = forall s. Stream (s -> m (Step a s)) (m s)
instance Monad m => Functor (Stream m) where
fmap = map
toList :: (Functor m, Monad m) => Stream m a -> m [a]
toList (Stream next s0) = unfold =<< s0
where
unfold !s = do
step <- next s
case step of
Done -> return []
Skip s' -> unfold s'
Yield x s' -> (x :) <$> unfold s'
fromList :: Monad m => [a] -> Stream m a
fromList xs = Stream next (return xs)
where
next [] = return Done
next (x:xs') = return $ Yield x xs'
append :: (Functor m, Monad m) => Stream m a -> Stream m a -> Stream m a
append (Stream next0 s0) (Stream next1 s1) = Stream next (Left <$> s0)
where
next (Left s) = do
step <- next0 s
case step of
Done -> Skip . Right <$> s1
Skip s' -> return $ Skip (Left s')
Yield x s' -> return $ Yield x (Left s')
next (Right s) = do
step <- next1 s
return $ case step of
Done -> Done
Skip s' -> Skip (Right s')
Yield x s' -> Yield x (Right s')
cons :: (Functor m, Monad m) => a -> Stream m a -> Stream m a
cons w (Stream next0 s0) = Stream next ((,) S2 <$> s0)
where
next (S2, s) = return $ Yield w (S1, s)
next (S1, s) = do
step <- next0 s
return $ case step of
Done -> Done
Skip s' -> Skip (S1, s')
Yield x s' -> Yield x (S1, s')
snoc :: (Functor m, Monad m) => Stream m a -> a -> Stream m a
snoc (Stream next0 s0) y = Stream next (Just <$> s0)
where
next Nothing = return Done
next (Just s) = do
step <- next0 s
return $ case step of
Done -> Yield y Nothing
Skip s' -> Skip (Just s')
Yield x s' -> Yield x (Just s')
head :: Monad m => Stream m a -> m (Maybe a)
head (Stream next s0) = loop =<< s0
where
loop !s = do
step <- next s
case step of
Yield x _ -> return $ Just x
Skip s' -> loop s'
Done -> return Nothing
last :: Monad m => Stream m a -> m (Maybe a)
last (Stream next s0) = loop =<< s0
where
loop !s = do
step <- next s
case step of
Done -> return Nothing
Skip s' -> loop s'
Yield x s' -> loop' x s'
loop' x !s = do
step <- next s
case step of
Done -> return $ Just x
Skip s' -> loop' x s'
Yield x' s' -> loop' x' s'
data Switch = S1 | S2
tail :: (Functor m, Monad m) => Stream m a -> Stream m a
tail (Stream next0 s0) = Stream next ((,) S1 <$> s0)
where
next (S1, s) = do
step <- next0 s
return $ case step of
Done -> Done
Skip s' -> Skip (S1, s')
Yield _ s' -> Skip (S2, s')
next (S2, s) = do
step <- next0 s
return $ case step of
Done -> Done
Skip s' -> Skip (S2, s')
Yield x s' -> Yield x (S2, s')
init :: (Functor m, Monad m) => Stream m a -> Stream m a
init (Stream next0 s0) = Stream next ((,) Nothing <$> s0)
where
next (Nothing, s) = do
step <- next0 s
return $ case step of
Done -> Done
Skip s' -> Skip (Nothing, s')
Yield x s' -> Skip (Just x , s')
next (Just x, s) = do
step <- next0 s
return $ case step of
Done -> Done
Skip s' -> Skip (Just x , s')
Yield x' s' -> Yield x (Just x', s')
null :: Monad m => Stream m a -> m Bool
null (Stream next s0) = loop =<< s0
where
loop !s = do
step <- next s
case step of
Done -> return True
Yield _ _ -> return False
Skip s' -> loop s'
length :: Monad m => Stream m a -> m Int
length (Stream next s0) = loop 0 =<< s0
where
loop !z !s = do
step <- next s
case step of
Done -> return z
Skip s' -> loop z s'
Yield _ s' -> loop (z+1) s'
elem :: (Eq a, Monad m) => a -> Stream m a -> m Bool
elem x (Stream next s0) = loop =<< s0
where
loop !s = do
step <- next s
case step of
Done -> return False
Skip s' -> loop s'
Yield y s' | y == x -> return True
| otherwise -> loop s'
notElem :: (Eq a, Monad m) => a -> Stream m a -> m Bool
notElem x s = elem x s >>= return . not
lookup :: (Eq a, Monad m) => a -> Stream m (a, b) -> m (Maybe b)
lookup key (Stream next s0) = loop =<< s0
where
loop !s = do
step <- next s
case step of
Done -> return Nothing
Skip s' -> loop s'
Yield (x, y) s' | key == x -> return $ Just y
| otherwise -> loop s'
find :: Monad m => (a -> Bool) -> Stream m a -> m (Maybe a)
find p = head . filter p
filter :: Monad m => (a -> Bool) -> Stream m a -> Stream m a
filter p (Stream next0 s0) = Stream next s0
where
next !s = do
step <- next0 s
return $ case step of
Done -> Done
Skip s' -> Skip s'
Yield x s' | p x -> Yield x s'
| otherwise -> Skip s'
map :: Monad m => (a -> b) -> Stream m a -> Stream m b
map f (Stream next0 s0) = Stream next s0
where
next !s = do
step <- next0 s
return $ case step of
Done -> Done
Skip s' -> Skip s'
Yield x s' -> Yield (f x) s'
mapM :: (Functor m, Monad m) => (a -> m b) -> Stream m a -> Stream m b
mapM f (Stream next0 s0) = Stream next s0
where
next !s = do
step <- next0 s
case step of
Done -> return Done
Skip s' -> return $ Skip s'
Yield x s' -> (`Yield` s') <$> f x
mapM_ :: (Functor m, Monad m) => (a -> m b) -> Stream m a -> Stream m ()
mapM_ f s = Stream go (return ())
where
go _ = foldM_ (\ _ -> void . f) () s >> return Done
reverse :: (Functor m, Monad m) => Stream m a -> m (Stream m a)
reverse = foldl' (flip cons) (fromList [])
intersperse :: (Functor m, Monad m) => a -> Stream m a -> Stream m a
intersperse sep (Stream next0 s0) = Stream next ((,,) Nothing S1 <$> s0)
where
next (Nothing, S1, s) = do
step <- next0 s
return $ case step of
Done -> Done
Skip s' -> Skip (Nothing, S1, s')
Yield x s' -> Skip (Just x , S1, s')
next (Just x, S1, s) = return $ Yield x (Nothing, S2, s)
next (Nothing, S2, s) = do
step <- next0 s
return $ case step of
Done -> Done
Skip s' -> Skip (Nothing, S2, s')
Yield x s' -> Yield sep (Just x , S1, s')
next (Just _, S2, _) = error "Data.Stream.Monadic.intersperse: impossible"
intercalate :: (Functor m, Monad m) => Stream m a -> Stream m [a] -> Stream m a
intercalate sep s = first s `append` rest s
where
first = concat . take 1
rest = concatMap (append sep . fromList) . drop 1
foldMap :: (Monoid m, Functor n, Monad n) => (a -> m) -> Stream n a -> n m
foldMap f (Stream next s0) = loop mempty =<< s0
where
loop z !s = do
step <- next s
case step of
Done -> return z
Skip s' -> loop z s'
Yield x s' -> loop (z <> f x) s'
foldl :: Monad m => (b -> a -> b) -> b -> Stream m a -> m b
foldl f z0 (Stream next s0) = loop z0 =<< s0
where
loop z !s = do
step <- next s
case step of
Done -> return z
Skip s' -> loop z s'
Yield x s' -> loop (f z x) s'
foldl' :: Monad m => (b -> a -> b) -> b -> Stream m a -> m b
foldl' f z0 (Stream next s0) = loop z0 =<< s0
where
loop !z !s = do
step <- next s
case step of
Done -> return z
Skip s' -> loop z s'
Yield x s' -> loop (f z x) s'
foldr :: (Functor m, Monad m) => (a -> b -> b) -> b -> Stream m a -> m b
foldr f z (Stream next s0) = loop =<< s0
where
loop !s = do
step <- next s
case step of
Done -> return z
Skip s' -> loop s'
Yield x s' -> f x <$> loop s'
foldM :: Monad m => (b -> a -> m b) -> b -> Stream m a -> m b
foldM f z0 (Stream next s0) = loop z0 =<< s0
where
loop z !s = do
step <- next s
case step of
Done -> return z
Skip s' -> loop z s'
Yield x s' -> f z x >>= (`loop` s')
foldM_ :: Monad m => (b -> a -> m b) -> b -> Stream m a -> m ()
foldM_ f z s = foldM f z s >> return ()
concat :: (Functor m, Monad m) => Stream m [a] -> Stream m a
concat = concatMap fromList
concatMap :: (Functor m, Monad m) => (a -> Stream m b) -> Stream m a -> Stream m b
concatMap f (Stream next0 s0) = Stream next ((,) Nothing <$> s0)
where
next (Nothing, s) = do
step <- next0 s
return $ case step of
Done -> Done
Skip s' -> Skip (Nothing , s')
Yield x s' -> Skip (Just (f x), s')
next (Just (Stream g t), s) = do
step <- g =<< t
return $ case step of
Done -> Skip (Nothing , s)
Skip t' -> Skip (Just (Stream g (return t')), s)
Yield x t' -> Yield x (Just (Stream g (return t')), s)
and :: (Functor m, Monad m) => Stream m Bool -> m Bool
and = foldr (&&) True
or :: (Functor m, Monad m) => Stream m Bool -> m Bool
or = foldr (||) False
any :: Monad m => (a -> Bool) -> Stream m a -> m Bool
any p (Stream next s0) = loop =<< s0
where
loop !s = do
step <- next s
case step of
Done -> return False
Skip s' -> loop s'
Yield x s' | p x -> return True
| otherwise -> loop s'
all :: Monad m => (a -> Bool) -> Stream m a -> m Bool
all p (Stream next s0) = loop =<< s0
where
loop !s = do
step <- next s
case step of
Done -> return True
Skip s' -> loop s'
Yield x s' | p x -> loop s'
| otherwise -> return False
sum :: (Num a, Monad m) => Stream m a -> m a
sum (Stream next s0) = loop 0 =<< s0
where
loop !a !s = do
step <- next s
case step of
Done -> return a
Skip s' -> loop a s'
Yield x s' -> loop (a + x) s'
product :: (Num a, Monad m) => Stream m a -> m a
product (Stream next s0) = loop 1 =<< s0
where
loop !a !s = do
step <- next s
case step of
Done -> return a
Skip s' -> loop a s'
Yield x s' -> loop (a * x) s'
scanl :: (Functor m, Monad m) => (b -> a -> b) -> b -> Stream m a -> Stream m b
scanl f z0 = go . (`snoc` undefined)
where
go (Stream step s0) = Stream (next step) ((,) z0 <$> s0)
next step (z, s) = do
step' <- step s
return $ case step' of
Done -> Done
Skip s' -> Skip (z , s')
Yield x s' -> Yield z (f z x, s')
iterate :: Monad m => (a -> a) -> a -> Stream m a
iterate f x0 = Stream next (return x0)
where
next x = return $ Yield x (f x)
repeat :: Monad m => a -> Stream m a
repeat x = Stream next (return ())
where
next _ = return $ Yield x ()
replicate :: Monad m => Int -> a -> Stream m a
replicate n x = Stream next (return n)
where
next !i | i <= 0 = return Done
| otherwise = return $ Yield x (i1)
cycle :: (Functor m, Monad m) => Stream m a -> Stream m a
cycle (Stream next0 s0) = Stream next ((,) S1 <$> s0)
where
next (S1, s) = do
step <- next0 s
return $ case step of
Done -> Done
Skip s' -> Skip (S1, s')
Yield x s' -> Yield x (S2, s')
next (S2, s) = do
step <- next0 s
case step of
Done -> Skip . (,) S2 <$> s0
Skip s' -> return $ Skip (S2, s')
Yield x s' -> return $ Yield x (S2, s')
unfoldr :: Monad m => (b -> Maybe (a, b)) -> b -> Stream m a
unfoldr f s0 = Stream next (return s0)
where
next s = return $ case f s of
Nothing -> Done
Just (w, s') -> Yield w s'
unfoldrM :: (Functor m, Monad m) => (b -> Maybe (a, m b)) -> m b -> Stream m a
unfoldrM f = Stream next
where
next s = case f s of
Nothing -> return Done
Just (w, s') -> Yield w <$> s'
isPrefixOf :: (Eq a, Monad m) => Stream m a -> Stream m a -> m Bool
isPrefixOf (Stream nexta sa0) (Stream nextb sb0) = do
sa0' <- sa0
sb0' <- sb0
loop sa0' sb0' Nothing
where
loop !sa !sb Nothing = do
stepa <- nexta sa
case stepa of
Done -> return True
Skip sa' -> loop sa' sb Nothing
Yield x sa' -> loop sa' sb (Just x)
loop !sa !sb (Just x) = do
stepb <- nextb sb
case stepb of
Done -> return False
Skip sb' -> loop sa sb' (Just x)
Yield y sb' | x == y -> loop sa sb' Nothing
| otherwise -> return False
isSuffixOf :: (Eq a, Functor m, Monad m) => Stream m a -> Stream m a -> m Bool
isSuffixOf sa sb = do
ra <- reverse sa
rb <- reverse sb
ra `isPrefixOf` rb
take :: (Functor m, Monad m) => Int -> Stream m a -> Stream m a
take n0 (Stream next0 s0) = Stream next ((,) n0 <$> s0)
where
next (!n, s)
| n <= 0 = return Done
| otherwise = do
step <- next0 s
return $ case step of
Done -> Done
Skip s' -> Skip (n , s')
Yield x s' -> Yield x (n1, s')
drop :: (Functor m, Monad m) => Int -> Stream m a -> Stream m a
drop n0 (Stream next0 s0) = Stream next ((,) (Just (max 0 n0)) <$> s0)
where
next (Just !n, s)
| n == 0 = return $ Skip (Nothing, s)
| otherwise = do
step <- next0 s
return $ case step of
Done -> Done
Skip s' -> Skip (Just n , s')
Yield _ s' -> Skip (Just (n1), s')
next (Nothing, s) = do
step <- next0 s
return $ case step of
Done -> Done
Skip s' -> Skip (Nothing, s')
Yield x s' -> Yield x (Nothing, s')
splitAt :: (Functor m, Monad m) => Int -> Stream m a -> (Stream m a, Stream m a)
splitAt n s = (take n s, drop n s)
takeWhile :: Monad m => (a -> Bool) -> Stream m a -> Stream m a
takeWhile p (Stream next0 s0) = Stream next s0
where
next !s = do
step <- next0 s
return $ case step of
Done -> Done
Skip s' -> Skip s'
Yield x s' | p x -> Yield x s'
| otherwise -> Done
dropWhile :: (Functor m, Monad m) => (a -> Bool) -> Stream m a -> Stream m a
dropWhile p (Stream next0 s0) = Stream next ((,) S1 <$> s0)
where
next (S1, s) = do
step <- next0 s
return $ case step of
Done -> Done
Skip s' -> Skip (S1, s')
Yield x s' | p x -> Skip (S1, s')
| otherwise -> Yield x (S2, s')
next (S2, s) = do
step <- next0 s
return $ case step of
Done -> Done
Skip s' -> Skip (S2, s')
Yield x s' -> Yield x (S2, s')
span :: (Functor m, Monad m) => (a -> Bool) -> Stream m a -> (Stream m a, Stream m a)
span p s = (takeWhile p s, dropWhile p s)
break :: (Functor m, Monad m) => (a -> Bool) -> Stream m a -> (Stream m a, Stream m a)
break p = span (not . p)
zip :: (Functor m, Applicative m, Monad m)
=> Stream m a
-> Stream m b
-> Stream m (a, b)
zip = zipWith (,)
zip3 :: (Functor m, Applicative m, Monad m)
=> Stream m a
-> Stream m b
-> Stream m c
-> Stream m (a, b, c)
zip3 = zipWith3 (,,)
zip4 :: (Functor m, Applicative m, Monad m)
=> Stream m a
-> Stream m b
-> Stream m c
-> Stream m d
-> Stream m (a, b, c, d)
zip4 = zipWith4 (,,,)
zipWith :: (Functor m, Applicative m, Monad m)
=> (a -> b -> c)
-> Stream m a
-> Stream m b
-> Stream m c
zipWith f (Stream nexta sa0) (Stream nextb sb0) =
Stream next ((,,) Nothing <$> sa0 <*> sb0)
where
next (Nothing, sa, sb) = do
step <- nexta sa
return $ case step of
Done -> Done
Skip sa' -> Skip (Nothing, sa', sb)
Yield a sa' -> Skip (Just a , sa', sb)
next (Just a, sa', sb) = do
step <- nextb sb
return $ case step of
Done -> Done
Skip sb' -> Skip (Just a, sa', sb')
Yield b sb' -> Yield (f a b) (Nothing, sa', sb')
zipWith3 :: (Functor m, Applicative m , Monad m)
=> (a -> b -> c -> d)
-> Stream m a
-> Stream m b
-> Stream m c
-> Stream m d
zipWith3 f (Stream nexta sa0)
(Stream nextb sb0)
(Stream nextc sc0)
= Stream next ((,,,) Nothing <$> sa0 <*> sb0 <*> sc0)
where
next (Nothing, sa, sb, sc) = do
step <- nexta sa
return $ case step of
Done -> Done
Skip sa' -> Skip (Nothing , sa', sb, sc)
Yield a sa' -> Skip (Just (a, Nothing), sa', sb, sc)
next (Just (a, Nothing), sa', sb, sc) = do
step <- nextb sb
return $ case step of
Done -> Done
Skip sb' -> Skip (Just (a, Nothing), sa', sb', sc)
Yield b sb' -> Skip (Just (a, Just b ), sa', sb', sc)
next (Just (a, Just b), sa', sb', sc) = do
step <- nextc sc
return $ case step of
Done -> Done
Skip sc' -> Skip (Just (a, Just b), sa', sb', sc')
Yield c sc' -> Yield (f a b c) (Nothing , sa', sb', sc')
zipWith4 :: (Functor m, Applicative m , Monad m)
=> (a -> b -> c -> d -> e)
-> Stream m a
-> Stream m b
-> Stream m c
-> Stream m d
-> Stream m e
zipWith4 f (Stream nexta sa0)
(Stream nextb sb0)
(Stream nextc sc0)
(Stream nextd sd0)
= Stream next ((,,,,) Nothing <$> sa0 <*> sb0 <*> sc0 <*> sd0)
where
next (Nothing, sa, sb, sc, sd) = do
step <- nexta sa
return $ case step of
Done -> Done
Skip sa' -> Skip (Nothing , sa', sb, sc, sd)
Yield a sa' -> Skip (Just (a, Nothing), sa', sb, sc, sd)
next (Just (a, Nothing), sa', sb, sc, sd) = do
step <- nextb sb
return $ case step of
Done -> Done
Skip sb' -> Skip (Just (a, Nothing) , sa', sb', sc, sd)
Yield b sb' -> Skip (Just (a, Just (b, Nothing)), sa', sb', sc, sd)
next (Just (a, Just (b, Nothing)), sa', sb', sc, sd) = do
step <- nextc sc
return $ case step of
Done -> Done
Skip sc' -> Skip (Just (a, Just (b, Nothing)), sa', sb', sc', sd)
Yield c sc' -> Skip (Just (a, Just (b, Just c)) , sa', sb', sc', sd)
next (Just (a, Just (b, Just c)), sa', sb', sc', sd) = do
step <- nextd sd
return $ case step of
Done -> Done
Skip sd' -> Skip (Just (a, Just (b, Just c)), sa', sb', sc', sd')
Yield d sd' -> Yield (f a b c d) (Nothing , sa', sb', sc', sd')
unzip :: (Functor m, Monad m) => Stream m (a, b) -> m ([a], [b])
unzip = foldr (\ (a,b) ~(as,bs) -> (a:as, b:bs)) ([],[])
unzip3 :: (Functor m, Monad m) => Stream m (a, b, c) -> m ([a], [b], [c])
unzip3 = foldr (\ (a,b,c) ~(as,bs,cs) -> (a:as, b:bs, c:cs)) ([],[],[])
unzip4 :: (Functor m, Monad m) => Stream m (a, b, c, d) -> m ([a], [b], [c], [d])
unzip4 = foldr (\ (a,b,c,d) ~(as,bs,cs,ds) -> (a:as, b:bs, c:cs, d:ds)) ([],[],[],[])
delete :: (Eq a, Functor m, Monad m) => a -> Stream m a -> Stream m a
delete = deleteBy (==)
insert :: (Ord a, Functor m, Monad m) => a -> Stream m a -> Stream m a
insert = insertBy compare
deleteBy :: (Functor m, Monad m)
=> (a -> a -> Bool)
-> a
-> Stream m a
-> Stream m a
deleteBy eq a (Stream next0 s0) = Stream next ((,) S1 <$> s0)
where
next (S1, s) = do
step <- next0 s
return $ case step of
Done -> Done
Skip s' -> Skip (S1, s')
Yield x s' | a `eq` x -> Skip (S2, s')
| otherwise -> Yield x (S1, s')
next (S2, s) = do
step <- next0 s
return $ case step of
Done -> Done
Skip s' -> Skip (S2, s')
Yield x s' -> Yield x (S2, s')
insertBy :: (Functor m, Monad m)
=> (a -> a -> Ordering)
-> a
-> Stream m a
-> Stream m a
insertBy cmp x (Stream next0 s0) = Stream next ((,,) S2 Nothing <$> s0)
where
next (S2, Nothing, s) = do
step <- next0 s
return $ case step of
Done -> Yield x (S1, Nothing, s )
Skip s' -> Skip (S2, Nothing, s')
Yield y s' | GT == cmp x y -> Yield y (S2, Nothing, s')
| otherwise -> Yield x (S1, Just y , s )
next (S2, Just _, _) = error "Data.Stream.Monadic.insertBy: impossible"
next (S1, Just y, s) = return $ Yield y (S1, Nothing, s)
next (S1, Nothing, s) = do
step <- next0 s
return $ case step of
Done -> Done
Skip s' -> Skip (S1, Nothing, s')
Yield y s' -> Yield y (S1, Nothing, s')
genericLength :: (Num i, Functor m, Monad m) => Stream m a -> m i
genericLength (Stream next s0) = loop =<< s0
where
loop !s = do
step <- next s
case step of
Done -> return 0
Skip s' -> loop s'
Yield _ s' -> (1 +) <$> loop s'
genericTake :: (Integral i, Functor m, Monad m) => i -> Stream m a -> Stream m a
genericTake n0 (Stream next0 s0) = Stream next ((,) n0 <$> s0)
where
next (0, _) = return Done
next (n, s) = do
step <- next0 s
return $ case step of
Done -> Done
Skip s' -> Skip (n , s')
Yield x s'
| n > 0 -> Yield x (n1, s')
| otherwise -> error "List.genericTake: negative argument"
genericDrop :: (Integral i, Functor m, Monad m) => i -> Stream m a -> Stream m a
genericDrop n0 (Stream next0 s0) = Stream next ((,) (Just n0) <$> s0)
where
next (Just 0, s) = return $ Skip (Nothing, s)
next (Just n, s) = do
step <- next0 s
return $ case step of
Done -> Done
Skip s' -> Skip (Just n , s')
Yield _ s' | n > 0 -> Skip (Just (n1), s')
| otherwise -> error "List.genericDrop: negative argument"
next (Nothing, s) = do
step <- next0 s
return $ case step of
Done -> Done
Skip s' -> Skip (Nothing, s')
Yield x s' -> Yield x (Nothing, s')
genericSplitAt :: (Integral i, Functor m, Monad m)
=> i
-> Stream m a
-> (Stream m a, Stream m a)
genericSplitAt i s = (genericTake i s, genericDrop i s)
genericReplicate :: (Integral i, Functor m, Monad m) => i -> a -> Stream m a
genericReplicate n = genericTake n . repeat
enumFromToInt :: Monad m => Int -> Int -> Stream m Int
enumFromToInt x y = trace "enumFromToInt" $ Stream next (return x)
where
next !n
| n > y = return Done
| otherwise = return $ Yield n (n+1)
enumDeltaInteger :: Monad m => Integer -> Integer -> Stream m Integer
enumDeltaInteger a d = trace "enumDeltaInteger" $ Stream next (return a)
where
next !x = return $ Yield x (x+d)
enumFromToChar :: Monad m => Char -> Char -> Stream m Char
enumFromToChar x y = Stream next (return (ord x))
where
m = ord y
next !n
| n > m = return Done
| otherwise = return $ Yield (chr n) (n+1)