list-t 1.0.5.1 → 1.0.5.2
raw patch · 5 files changed
+217/−200 lines, 5 filesdep ~logictsetup-changedPVP ok
version bump matches the API change (PVP)
Dependency ranges changed: logict
API changes (from Hackage documentation)
Files
- Setup.hs +0/−2
- library/ListT.hs +160/−129
- library/ListT/Prelude.hs +21/−22
- list-t.cabal +10/−8
- tests/Main.hs +26/−39
− Setup.hs
@@ -1,2 +0,0 @@-import Distribution.Simple-main = defaultMain
library/ListT.hs view
@@ -1,59 +1,66 @@ module ListT-(- ListT(..),- -- * Execution utilities- uncons,- head,- tail,- null,- alternate,- alternateHoisting,- fold,- foldMaybe,- applyFoldM,- toList,- toReverseList,- traverse_,- splitAt,- -- * Construction utilities- cons,- fromFoldable,- fromMVar,- unfold,- unfoldM,- repeat,- -- * Transformation utilities- -- | - -- These utilities only accumulate the transformations- -- without actually traversing the stream.- -- They only get applied in a single traversal, - -- which only happens at the execution.- traverse,- take,- drop,- slice,-)+ ( ListT (..),++ -- * Execution utilities+ uncons,+ head,+ tail,+ null,+ alternate,+ alternateHoisting,+ fold,+ foldMaybe,+ applyFoldM,+ toList,+ toReverseList,+ traverse_,+ splitAt,++ -- * Construction utilities+ cons,+ fromFoldable,+ fromMVar,+ unfold,+ unfoldM,+ repeat,++ -- * Transformation utilities++ -- |+ -- These utilities only accumulate the transformations+ -- without actually traversing the stream.+ -- They only get applied in a single traversal,+ -- which only happens at the execution.+ traverse,+ take,+ drop,+ slice,+ ) where -import ListT.Prelude hiding (uncons, toList, yield, fold, traverse, head, tail, take, drop, repeat, null, traverse_, splitAt) import Control.Monad+import ListT.Prelude hiding (drop, fold, head, null, repeat, splitAt, tail, take, toList, traverse, traverse_, uncons, yield) -- | -- A proper implementation of the list monad-transformer. -- Useful for streaming of monadic data structures.--- +-- -- Since it has instances of 'MonadPlus' and 'Alternative', -- you can use general utilities packages like -- <http://hackage.haskell.org/package/monadplus "monadplus"> -- with it.-newtype ListT m a =- ListT (m (Maybe (a, ListT m a)))+newtype ListT m a+ = ListT (m (Maybe (a, ListT m a))) deriving (Foldable, Traversable, Generic) deriving instance Show (m (Maybe (a, ListT m a))) => Show (ListT m a)+ deriving instance Read (m (Maybe (a, ListT m a))) => Read (ListT m a)+ deriving instance Eq (m (Maybe (a, ListT m a))) => Eq (ListT m a)+ deriving instance Ord (m (Maybe (a, ListT m a))) => Ord (ListT m a)+ deriving instance (Typeable m, Typeable a, Data (m (Maybe (a, ListT m a)))) => Data (ListT m a) instance Eq1 m => Eq1 (ListT m) where@@ -94,8 +101,8 @@ instance Monad m => Semigroup (ListT m a) where (<>) (ListT m1) (ListT m2) = ListT $- m1 >>=- \case+ m1+ >>= \case Nothing -> m2 Just (h1, s1') ->@@ -103,7 +110,7 @@ instance Monad m => Monoid (ListT m a) where mempty =- ListT $ + ListT $ return Nothing mappend = (<>) @@ -114,10 +121,11 @@ ListT . (fmap . fmap) (bimapPair' f go) . uncons instance (Monad m, Functor m) => Applicative (ListT m) where- pure = - return- (<*>) = + pure a =+ ListT $ return (Just (a, (ListT (return Nothing))))+ (<*>) = ap+ -- This is just like liftM2, but it uses fmap over the second -- action. liftM2 can't do that, because it has to deal with -- the possibility that someone defines liftA2 = liftM2 and@@ -125,25 +133,24 @@ liftA2 f m1 m2 = do x1 <- m1 fmap (f x1) m2- (*>) = (>>) instance (Monad m, Functor m) => Alternative (ListT m) where- empty = + empty = inline mempty- (<|>) = + (<|>) = inline mappend instance Monad m => Monad (ListT m) where- return a =- ListT $ return (Just (a, (ListT (return Nothing))))+ return = pure+ -- We use a go function so GHC can inline k2 -- if it likes. (>>=) s10 k2 = go s10 where go s1 = ListT $- uncons s1 >>=- \case+ uncons s1+ >>= \case Nothing -> return Nothing Just (h1, t1) ->@@ -154,9 +161,9 @@ inline mempty instance Monad m => MonadPlus (ListT m) where- mzero = + mzero = inline mempty- mplus = + mplus = inline mappend instance MonadTrans ListT where@@ -183,11 +190,13 @@ lift . liftBase instance MonadBaseControl b m => MonadBaseControl b (ListT m) where- type StM (ListT m) a =- StM m (Maybe (a, ListT m a))+ type+ StM (ListT m) a =+ StM m (Maybe (a, ListT m a)) liftBaseWith runToBase =- lift $ liftBaseWith $ \runInner -> - runToBase $ runInner . uncons+ lift $+ liftBaseWith $ \runInner ->+ runToBase $ runInner . uncons restoreM inner = lift (restoreM inner) >>= \case Nothing -> mzero@@ -212,40 +221,55 @@ instance Monad m => MonadLogic (ListT m) where msplit (ListT m) = lift m - interleave m1 m2 = ListT $ uncons m1 >>= \case- Nothing -> uncons m2- Just (a, m1') -> uncons $ cons a (interleave m2 m1')+ interleave m1 m2 =+ ListT $+ uncons m1 >>= \case+ Nothing -> uncons m2+ Just (a, m1') -> uncons $ cons a (interleave m2 m1') - m >>- f = ListT $ uncons m >>= \case- Nothing -> uncons empty- Just (a, m') -> uncons $ interleave (f a) (m' >>- f)+ m >>- f =+ ListT $+ uncons m >>= \case+ Nothing -> uncons empty+ Just (a, m') -> uncons $ interleave (f a) (m' >>- f) - ifte t th el = ListT $ uncons t >>= \case- Nothing -> uncons el- Just (a,m) -> uncons $ th a <|> (m >>= th)+ ifte t th el =+ ListT $+ uncons t >>= \case+ Nothing -> uncons el+ Just (a, m) -> uncons $ th a <|> (m >>= th) - once (ListT m) = ListT $ m >>= \case- Nothing -> uncons empty- Just (a, _) -> uncons (return a)+ once (ListT m) =+ ListT $+ m >>= \case+ Nothing -> uncons empty+ Just (a, _) -> uncons (return a) - lnot (ListT m) = ListT $ m >>= \case- Nothing -> uncons (return ())- Just _ -> uncons empty+ lnot (ListT m) =+ ListT $+ m >>= \case+ Nothing -> uncons (return ())+ Just _ -> uncons empty instance MonadZip m => MonadZip (ListT m) where mzipWith f = go where go (ListT m1) (ListT m2) =- ListT $ mzipWith (mzipWith $- \(a, as) (b, bs) -> (f a b, go as bs)) m1 m2+ ListT $+ mzipWith+ ( mzipWith $+ \(a, as) (b, bs) -> (f a b, go as bs)+ )+ m1+ m2 munzip (ListT m)- | (l, r) <- munzip (fmap go m)- = (ListT l, ListT r)+ | (l, r) <- munzip (fmap go m) =+ (ListT l, ListT r) where go Nothing = (Nothing, Nothing)- go (Just ((a, b), listab))- = (Just (a, la), Just (b, lb))+ go (Just ((a, b), listab)) =+ (Just (a, la), Just (b, lb)) where -- If the underlying munzip is careful not to leak memory, then we -- don't want to defeat it. We need to be sure that la and lb are@@ -257,6 +281,7 @@ (la, lb) = remains -- * Execution in the inner monad+ ------------------------- -- |@@ -269,21 +294,21 @@ -- | -- Execute, getting the head. Returns nothing if it's empty.-{-# INLINABLE head #-}+{-# INLINEABLE head #-} head :: Monad m => ListT m a -> m (Maybe a) head = fmap (fmap fst) . uncons -- | -- Execute, getting the tail. Returns nothing if it's empty.-{-# INLINABLE tail #-}+{-# INLINEABLE tail #-} tail :: Monad m => ListT m a -> m (Maybe (ListT m a)) tail = fmap (fmap snd) . uncons -- | -- Execute, checking whether it's empty.-{-# INLINABLE null #-}+{-# INLINEABLE null #-} null :: Monad m => ListT m a -> m Bool null = fmap (maybe True (const False)) . uncons@@ -291,41 +316,44 @@ -- | -- Execute in the inner monad, -- using its '(<|>)' function on each entry.-{-# INLINABLE alternate #-}+{-# INLINEABLE alternate #-} alternate :: (Alternative m, Monad m) => ListT m a -> m a-alternate (ListT m) = m >>= \case- Nothing -> empty- Just (a, as) -> pure a <|> alternate as+alternate (ListT m) =+ m >>= \case+ Nothing -> empty+ Just (a, as) -> pure a <|> alternate as -- | -- Use a monad morphism to convert a 'ListT' to a similar -- monad, such as '[]'.--- +-- -- A more efficient alternative to @'alternate' . 'hoist' f@.-{-# INLINABLE alternateHoisting #-}+{-# INLINEABLE alternateHoisting #-} alternateHoisting :: (Monad n, Alternative n) => (forall a. m a -> n a) -> ListT m a -> n a alternateHoisting f = go where- go (ListT m) = f m >>= \case- Nothing -> empty- Just (a, as) -> pure a <|> go as+ go (ListT m) =+ f m >>= \case+ Nothing -> empty+ Just (a, as) -> pure a <|> go as -- | -- Execute, applying a left fold.-{-# INLINABLE fold #-}+{-# INLINEABLE fold #-} fold :: Monad m => (r -> a -> m r) -> r -> ListT m a -> m r-fold s r = +fold s r = uncons >=> maybe (return r) (\(h, t) -> s r h >>= \r' -> fold s r' t) -- | -- A version of 'fold', which allows early termination.-{-# INLINABLE foldMaybe #-}+{-# INLINEABLE foldMaybe #-} foldMaybe :: Monad m => (r -> a -> m (Maybe r)) -> r -> ListT m a -> m r foldMaybe s r l =- fmap (maybe r id) $ runMaybeT $ do- (h, t) <- MaybeT $ uncons l- r' <- MaybeT $ s r h- lift $ foldMaybe s r' t+ fmap (maybe r id) $+ runMaybeT $ do+ (h, t) <- MaybeT $ uncons l+ r' <- MaybeT $ s r h+ lift $ foldMaybe s r' t -- | -- Apply a left fold abstraction from the \"foldl\" package.@@ -337,7 +365,7 @@ -- | -- Execute, folding to a list.-{-# INLINABLE toList #-}+{-# INLINEABLE toList #-} toList :: Monad m => ListT m a -> m [a] toList = liftM ($ []) . fold (\f e -> return $ f . (e :)) id@@ -345,21 +373,21 @@ -- | -- Execute, folding to a list in the reverse order. -- Performs more efficiently than 'toList'.-{-# INLINABLE toReverseList #-}+{-# INLINEABLE toReverseList #-} toReverseList :: Monad m => ListT m a -> m [a] toReverseList =- ListT.fold (\l -> return . (:l)) []+ ListT.fold (\l -> return . (: l)) [] -- |--- Execute, traversing the stream with a side effect in the inner monad. -{-# INLINABLE traverse_ #-}+-- Execute, traversing the stream with a side effect in the inner monad.+{-# INLINEABLE traverse_ #-} traverse_ :: Monad m => (a -> m ()) -> ListT m a -> m () traverse_ f = fold (const f) () -- | -- Execute, consuming a list of the specified length and returning the remainder stream.-{-# INLINABLE splitAt #-}+{-# INLINEABLE splitAt #-} splitAt :: Monad m => Int -> ListT m a -> m ([a], ListT m a) splitAt = \case@@ -369,11 +397,11 @@ Just (h, t) -> do (r1, r2) <- splitAt (pred n) t return (h : r1, r2)- _ -> \l -> + _ -> \l -> return ([], l) - -- * Construction+ ------------------------- -- |@@ -384,9 +412,9 @@ -- | -- Construct from any foldable.-{-# INLINABLE fromFoldable #-}+{-# INLINEABLE fromFoldable #-} fromFoldable :: (Monad m, Foldable f) => f a -> ListT m a-fromFoldable = +fromFoldable = foldr cons mzero -- |@@ -397,7 +425,7 @@ -- | -- Construct by unfolding a pure data structure.-{-# INLINABLE unfold #-}+{-# INLINEABLE unfold #-} unfold :: Monad m => (b -> Maybe (a, b)) -> b -> ListT m a unfold f s = maybe mzero (\(h, t) -> cons h (unfold f t)) (f s)@@ -407,44 +435,47 @@ -- -- This is the most memory-efficient way to construct ListT where -- the length depends on the inner monad.-{-# INLINABLE unfoldM #-}+{-# INLINEABLE unfoldM #-} unfoldM :: Monad m => (b -> m (Maybe (a, b))) -> b -> ListT m a-unfoldM f = go where- go s = ListT $ f s >>= \case- Nothing -> return Nothing- Just (a,r) -> return (Just (a, go r))+unfoldM f = go+ where+ go s =+ ListT $+ f s >>= \case+ Nothing -> return Nothing+ Just (a, r) -> return (Just (a, go r)) -- | -- Produce an infinite stream.-{-# INLINABLE repeat #-}+{-# INLINEABLE repeat #-} repeat :: Monad m => a -> ListT m a-repeat = +repeat = fix . cons - -- * Transformation+ ------------------------- -- | -- A transformation, -- which traverses the stream with an action in the inner monad.-{-# INLINABLE traverse #-}+{-# INLINEABLE traverse #-} traverse :: Monad m => (a -> m b) -> ListT m a -> ListT m b traverse f s =- lift (uncons s) >>= - mapM (\(h, t) -> lift (f h) >>= \h' -> cons h' (traverse f t)) >>=- maybe mzero return+ lift (uncons s)+ >>= mapM (\(h, t) -> lift (f h) >>= \h' -> cons h' (traverse f t))+ >>= maybe mzero return -- | -- A transformation, -- reproducing the behaviour of @Data.List.'Data.List.take'@.-{-# INLINABLE take #-}+{-# INLINEABLE take #-} take :: Monad m => Int -> ListT m a -> ListT m a take = \case n | n > 0 -> \t ->- lift (uncons t) >>= - \case+ lift (uncons t)+ >>= \case Nothing -> t Just (h, t) -> cons h (take (pred n) t) _ ->@@ -453,24 +484,24 @@ -- | -- A transformation, -- reproducing the behaviour of @Data.List.'Data.List.drop'@.-{-# INLINABLE drop #-}+{-# INLINEABLE drop #-} drop :: Monad m => Int -> ListT m a -> ListT m a drop = \case- n | n > 0 ->- lift . uncons >=> maybe mzero (drop (pred n) . snd)+ n+ | n > 0 ->+ lift . uncons >=> maybe mzero (drop (pred n) . snd) _ -> id -- | -- A transformation, -- which slices a list into chunks of the specified length.-{-# INLINABLE slice #-}+{-# INLINEABLE slice #-} slice :: Monad m => Int -> ListT m a -> ListT m [a]-slice n l = +slice n l = do (h, t) <- lift $ splitAt n l case h of [] -> mzero _ -> cons h (slice n t)-
library/ListT/Prelude.hs view
@@ -1,30 +1,29 @@ module ListT.Prelude-( - module Exports,- bimapPair',- secondPair',-)+ ( module Exports,+ bimapPair',+ secondPair',+ ) where import Control.Applicative as Exports import Control.Category as Exports import Control.Concurrent as Exports import Control.Exception as Exports-import Control.Foldl as Exports (Fold(..), FoldM(..))-import Control.Monad as Exports hiding (mapM_, sequence_, forM_, msum, mapM, sequence, forM, fail)+import Control.Foldl as Exports (Fold (..), FoldM (..))+import Control.Monad as Exports hiding (fail, forM, forM_, mapM, mapM_, msum, sequence, sequence_) import Control.Monad.Base as Exports import Control.Monad.Error.Class as Exports import Control.Monad.Fail as Exports import Control.Monad.Fix as Exports hiding (fix) import Control.Monad.IO.Class as Exports import Control.Monad.Logic.Class as Exports-import Control.Monad.Morph as Exports hiding (MonadTrans(..))+import Control.Monad.Morph as Exports hiding (MonadTrans (..)) import Control.Monad.Reader.Class as Exports-import Control.Monad.State.Class as Exports import Control.Monad.ST as Exports+import Control.Monad.State.Class as Exports import Control.Monad.Trans.Class as Exports import Control.Monad.Trans.Control as Exports hiding (embed, embed_)-import Control.Monad.Trans.Maybe as Exports hiding (liftCatch, liftCallCC)+import Control.Monad.Trans.Maybe as Exports hiding (liftCallCC, liftCatch) import Control.Monad.Zip as Exports import Data.Bits as Exports import Data.Bool as Exports@@ -39,17 +38,17 @@ import Data.Function as Exports hiding (id, (.)) import Data.Functor as Exports import Data.Functor.Classes as Exports-import Data.Int as Exports import Data.IORef as Exports+import Data.Int as Exports import Data.Ix as Exports-import Data.List as Exports hiding (sortOn, isSubsequenceOf, uncons, concat, foldr, foldl1, maximum, minimum, product, sum, all, and, any, concatMap, elem, foldl, foldr1, notElem, or, find, maximumBy, minimumBy, mapAccumL, mapAccumR, foldl')+import Data.List as Exports hiding (all, and, any, concat, concatMap, elem, find, foldl, foldl', foldl1, foldr, foldr1, isSubsequenceOf, mapAccumL, mapAccumR, maximum, maximumBy, minimum, minimumBy, notElem, or, product, sortOn, sum, uncons) import Data.Maybe as Exports-import Data.Monoid as Exports hiding (getLast, getFirst, (<>), Last, First)+import Data.Monoid as Exports hiding (First, Last, getFirst, getLast, (<>)) import Data.Ord as Exports import Data.Proxy as Exports import Data.Ratio as Exports-import Data.Semigroup as Exports import Data.STRef as Exports+import Data.Semigroup as Exports import Data.String as Exports import Data.Traversable as Exports import Data.Tuple as Exports@@ -61,12 +60,11 @@ import Foreign.Ptr as Exports import Foreign.StablePtr as Exports import Foreign.Storable as Exports-import GHC.Conc as Exports hiding (withMVar, threadWaitWriteSTM, threadWaitWrite, threadWaitReadSTM, threadWaitRead)-import GHC.Exts as Exports (lazy, inline, sortWith, groupWith)+import GHC.Conc as Exports hiding (threadWaitRead, threadWaitReadSTM, threadWaitWrite, threadWaitWriteSTM, withMVar)+import GHC.Exts as Exports (groupWith, inline, lazy, sortWith) import GHC.Generics as Exports (Generic) import GHC.IO.Exception as Exports import Numeric as Exports-import Prelude as Exports hiding (fail, concat, foldr, mapM_, sequence_, foldl1, maximum, minimum, product, sum, all, and, any, concatMap, elem, foldl, foldr1, notElem, or, mapM, sequence, id, (.)) import System.Environment as Exports import System.Exit as Exports import System.IO as Exports (Handle, hClose)@@ -76,19 +74,20 @@ import System.Mem.StableName as Exports import System.Timeout as Exports import Text.ParserCombinators.ReadP as Exports (ReadP, ReadS, readP_to_S, readS_to_P)-import Text.ParserCombinators.ReadPrec as Exports (ReadPrec, readPrec_to_P, readP_to_Prec, readPrec_to_S, readS_to_Prec)-import Text.Printf as Exports (printf, hPrintf)-import Text.Read as Exports (Read(..), readMaybe, readEither)+import Text.ParserCombinators.ReadPrec as Exports (ReadPrec, readP_to_Prec, readPrec_to_P, readPrec_to_S, readS_to_Prec)+import Text.Printf as Exports (hPrintf, printf)+import Text.Read as Exports (Read (..), readEither, readMaybe) import Unsafe.Coerce as Exports+import Prelude as Exports hiding (all, and, any, concat, concatMap, elem, fail, foldl, foldl1, foldr, foldr1, id, mapM, mapM_, maximum, minimum, notElem, or, product, sequence, sequence_, sum, (.)) -- | -- A slightly stricter version of Data.Bifunctor.bimap. -- There's no benefit to producing lazy pairs here. bimapPair' :: (a -> b) -> (c -> d) -> (a, c) -> (b, d)-bimapPair' f g = \(a,c) -> (f a, g c)+bimapPair' f g = \(a, c) -> (f a, g c) -- | -- A slightly stricter version of Data.Bifunctor.second -- that doesn't produce gratuitous lazy pairs. secondPair' :: (b -> c) -> (a, b) -> (a, c)-secondPair' f = \(a,b) -> (a, f b)+secondPair' f = \(a, b) -> (a, f b)
list-t.cabal view
@@ -1,5 +1,7 @@+cabal-version: 3.0+ name: list-t-version: 1.0.5.1+version: 1.0.5.2 synopsis: ListT done right description: A correct implementation of the list monad-transformer.@@ -12,17 +14,18 @@ copyright: (c) 2014, Nikita Volkov license: MIT license-file: LICENSE-build-type: Simple-cabal-version: >=1.10 source-repository head type: git location: git://github.com/nikita-volkov/list-t.git -library- hs-source-dirs: library+common language-settings default-extensions: BangPatterns, ConstraintKinds, DataKinds, DefaultSignatures, DeriveDataTypeable, DeriveFunctor, DeriveGeneric, DeriveTraversable, EmptyDataDecls, FlexibleContexts, FlexibleInstances, FunctionalDependencies, GADTs, GeneralizedNewtypeDeriving, LambdaCase, LiberalTypeSynonyms, MagicHash, MultiParamTypeClasses, MultiWayIf, NoImplicitPrelude, NoMonomorphismRestriction, OverloadedStrings, PatternGuards, ParallelListComp, PolyKinds, QuasiQuotes, RankNTypes, RecordWildCards, ScopedTypeVariables, StandaloneDeriving, TemplateHaskell, TupleSections, TypeFamilies, TypeOperators, UnboxedTuples, UndecidableInstances default-language: Haskell2010++library+ import: language-settings+ hs-source-dirs: library exposed-modules: ListT other-modules:@@ -30,7 +33,7 @@ build-depends: base >=4.11 && <5, foldl >=1 && <2,- logict >=0.7 && <0.8,+ logict >=0.7 && <0.9, mmorph ==1.*, monad-control >=0.3 && <2, mtl ==2.*,@@ -39,11 +42,10 @@ transformers-base ==0.4.* test-suite tests+ import: language-settings type: exitcode-stdio-1.0 hs-source-dirs: tests main-is: Main.hs- default-extensions: BangPatterns, ConstraintKinds, DataKinds, DefaultSignatures, DeriveDataTypeable, DeriveFunctor, DeriveGeneric, DeriveTraversable, EmptyDataDecls, FlexibleContexts, FlexibleInstances, FunctionalDependencies, GADTs, GeneralizedNewtypeDeriving, LambdaCase, LiberalTypeSynonyms, MagicHash, MultiParamTypeClasses, MultiWayIf, NoImplicitPrelude, NoMonomorphismRestriction, OverloadedStrings, PatternGuards, ParallelListComp, PolyKinds, QuasiQuotes, RankNTypes, RecordWildCards, ScopedTypeVariables, StandaloneDeriving, TemplateHaskell, TupleSections, TypeFamilies, TypeOperators, UnboxedTuples, UndecidableInstances- default-language: Haskell2010 build-depends: list-t, mmorph,
tests/Main.hs view
@@ -1,35 +1,29 @@ {-# OPTIONS_GHC -F -pgmF htfpp #-} import BasePrelude hiding (toList)-import MTLPrelude import Control.Monad.Morph-import Test.Framework import qualified ListT as L-+import MTLPrelude+import Test.Framework main = htfMain $ htf_thisModulesTests - -- * MMonad-------------------------- -- embed lift = id prop_mmonadLaw1 (l :: [Int]) = let s = L.fromFoldable l- in runIdentity $ streamsEqual s (embed lift s)+ in runIdentity $ streamsEqual s (embed lift s) -- embed f (lift m) = f m prop_mmonadLaw2 l = let s = (L.fromFoldable :: [Int] -> L.ListT Identity Int) l f = MaybeT . fmap Just run = runIdentity . L.toList . runMaybeT- in - run (f s) == - run (embed f (lift s))-+ in run (f s)+ == run (embed f (lift s)) -- * Applicative-------------------------- prop_applicativeIdentityLaw (l :: [Int]) = runIdentity $ streamsEqual (pure id <*> s) s@@ -40,13 +34,11 @@ \(ns :: [Int]) -> let a = fs <*> ns b = runIdentity (toList $ L.fromFoldable fs <*> L.fromFoldable ns)- in a == b+ in a == b where- fs = [(+1), (+3), (+5)]-+ fs = [(+ 1), (+ 3), (+ 5)] -- * Monad-------------------------- test_monadLaw1 = assertBool =<< streamsEqual (return a >>= k) (k a)@@ -57,12 +49,12 @@ test_monadLaw2 = assertBool =<< streamsEqual (m >>= return) m where- m = L.fromFoldable ['a'..'z']+ m = L.fromFoldable ['a' .. 'z'] test_monadLaw3 = assertBool =<< streamsEqual (m >>= (\x -> k x >>= h)) ((m >>= k) >>= h) where- m = L.fromFoldable ['a'..'z']+ m = L.fromFoldable ['a' .. 'z'] k a = return $ ord a h a = return $ a + 1 @@ -70,23 +62,21 @@ assertBool =<< streamsEqual (fmap f xs) (xs >>= return . f) where f = ord- xs = L.fromFoldable ['a'..'z']-+ xs = L.fromFoldable ['a' .. 'z'] -- * Monoid-------------------------- test_mappend =- assertBool =<< - streamsEqual - (L.fromFoldable [0..7]) - (L.fromFoldable [0..3] <> L.fromFoldable [4..7])+ assertBool+ =<< streamsEqual+ (L.fromFoldable [0 .. 7])+ (L.fromFoldable [0 .. 3] <> L.fromFoldable [4 .. 7]) test_mappendAndTake =- assertBool =<< - streamsEqual - (L.fromFoldable [0..5]) - (L.take 6 $ L.fromFoldable [0..3] <> L.fromFoldable [4..7])+ assertBool+ =<< streamsEqual+ (L.fromFoldable [0 .. 5])+ (L.take 6 $ L.fromFoldable [0 .. 3] <> L.fromFoldable [4 .. 7]) test_mappendDoesntCauseTraversal = do@@ -97,16 +87,14 @@ stream = do ref <- lift $ ask- x <- L.fromFoldable [0..4]- liftIO $ modifyIORef ref (+1)+ x <- L.fromFoldable [0 .. 4]+ liftIO $ modifyIORef ref (+ 1) return x - -- * Other-------------------------- test_repeat =- assertEqual [2,2,2] =<< do+ assertEqual [2, 2, 2] =<< do toList $ L.take 3 $ L.repeat (2 :: Int) test_traverseDoesntCauseTraversal =@@ -118,8 +106,8 @@ stream1 = do ref <- lift $ ask- x <- L.fromFoldable ['a'..'z']- liftIO $ modifyIORef ref (+1)+ x <- L.fromFoldable ['a' .. 'z']+ liftIO $ modifyIORef ref (+ 1) return x stream2 = L.traverse (return . toUpper) stream1@@ -135,18 +123,17 @@ stream = do ref <- lift $ ask- x <- L.fromFoldable [0..10]- liftIO $ modifyIORef ref (+1)+ x <- L.fromFoldable [0 .. 10]+ liftIO $ modifyIORef ref (+ 1) return x test_drop = assertEqual [3, 4] =<< do toList $ L.drop 2 $ L.fromFoldable [1 .. 4]- + test_slice = assertEqual ["abc", "def", "gh"] =<< do toList $ L.slice 3 $ L.fromFoldable ("abcdefgh" :: [Char])- toList :: Monad m => L.ListT m a -> m [a] toList = L.toList