From 449d48d379310d1b2a1b22be0c49a9ae29925dff Mon Sep 17 00:00:00 2001 From: Harendra Kumar Date: Thu, 17 Nov 2022 13:21:12 +0530 Subject: [PATCH] Remove deepseq and mtl dependencies from streamly-core --- benchmark/Streamly/Benchmark/Data/Array.hs | 6 +++ .../Streamly/Benchmark/Data/Array/Generic.hs | 6 +++ .../Streamly/Benchmark/Data/Array/Mut.hs | 5 ++ benchmark/Streamly/Benchmark/Data/Fold.hs | 13 +++++- .../Benchmark/Data/Stream/Eliminate.hs | 6 +++ .../Benchmark/Data/Stream/Generate.hs | 10 +++- .../Streamly/Benchmark/Data/Stream/Lift.hs | 13 +++--- .../Benchmark/Data/Stream/Transform.hs | 9 +++- benchmark/Streamly/Benchmark/Unicode/Char.hs | 12 +++-- benchmark/Streamly/Benchmark/Unicode/Utf8.hs | 4 +- .../Streamly/Internal/Data/Array/Generic.hs | 5 -- .../Streamly/Internal/Data/Array/Mut/Type.hs | 11 ----- core/src/Streamly/Internal/Data/Array/Type.hs | 10 ---- core/src/Streamly/Internal/Data/List.hs | 6 +-- .../Internal/Data/Parser/ParserD/Type.hs | 19 -------- .../Internal/Data/Parser/ParserK/Type.hs | 28 ++++------- .../Streamly/Internal/Data/Stream/StreamK.hs | 1 - .../Internal/Data/Stream/StreamK/Type.hs | 18 +------- .../Internal/Data/Stream/Transform.hs | 1 + .../src/Streamly/Internal/Data/Stream/Type.hs | 30 ------------ core/src/Streamly/Internal/Data/Stream/Zip.hs | 3 -- core/streamly-core.cabal | 3 -- hie.yaml | 2 + src/Streamly/Data/Array/Foreign.hs | 13 ++++++ .../Streamly/Internal/Data/Cont.hs | 0 src/Streamly/Internal/Data/Stream/Ahead.hs | 10 +++- src/Streamly/Internal/Data/Stream/Async.hs | 10 +++- .../Internal/Data/Stream/Instances.hs | 2 +- src/Streamly/Internal/Data/Stream/IsStream.hs | 10 +++- src/Streamly/Internal/Data/Stream/Parallel.hs | 10 +++- src/Streamly/Internal/Data/Stream/Serial.hs | 46 ++++++++++++++++++- src/Streamly/Internal/Unicode/Utf8.hs | 5 +- streamly.cabal | 1 + 33 files changed, 180 insertions(+), 148 deletions(-) rename {core/src => src}/Streamly/Internal/Data/Cont.hs (100%) diff --git a/benchmark/Streamly/Benchmark/Data/Array.hs b/benchmark/Streamly/Benchmark/Data/Array.hs index 77977518a..081fbf152 100644 --- a/benchmark/Streamly/Benchmark/Data/Array.hs +++ b/benchmark/Streamly/Benchmark/Data/Array.hs @@ -1,4 +1,5 @@ {-# OPTIONS_GHC -Wno-deprecations #-} +{-# OPTIONS_GHC -Wno-orphans #-} {-# LANGUAGE CPP #-} @@ -11,10 +12,15 @@ import qualified GHC.Exts as GHC -- import qualified Streamly.Data.Array as A import qualified Streamly.Internal.Data.Array as A + type Stream = A.Array #include "Streamly/Benchmark/Data/Array/Common.hs" +instance NFData (A.Array a) where + {-# INLINE rnf #-} + rnf _ = () + ------------------------------------------------------------------------------- -- Benchmark helpers ------------------------------------------------------------------------------- diff --git a/benchmark/Streamly/Benchmark/Data/Array/Generic.hs b/benchmark/Streamly/Benchmark/Data/Array/Generic.hs index 2b14587aa..67939aedb 100644 --- a/benchmark/Streamly/Benchmark/Data/Array/Generic.hs +++ b/benchmark/Streamly/Benchmark/Data/Array/Generic.hs @@ -1,4 +1,5 @@ {-# OPTIONS_GHC -Wno-deprecations #-} +{-# OPTIONS_GHC -Wno-orphans #-} {-# LANGUAGE CPP #-} @@ -8,10 +9,15 @@ import Control.DeepSeq (deepseq) import qualified Streamly.Internal.Data.Array.Generic as IA import qualified Streamly.Internal.Data.Array.Generic as A + type Stream = A.Array #include "Streamly/Benchmark/Data/Array/Common.hs" +instance NFData a => NFData (A.Array a) where + {-# INLINE rnf #-} + rnf = A.foldl' (\_ x -> rnf x) () + ------------------------------------------------------------------------------- -- Benchmark helpers ------------------------------------------------------------------------------- diff --git a/benchmark/Streamly/Benchmark/Data/Array/Mut.hs b/benchmark/Streamly/Benchmark/Data/Array/Mut.hs index 29e0051b6..4b8e841c9 100644 --- a/benchmark/Streamly/Benchmark/Data/Array/Mut.hs +++ b/benchmark/Streamly/Benchmark/Data/Array/Mut.hs @@ -1,4 +1,5 @@ {-# OPTIONS_GHC -Wno-deprecations #-} +{-# OPTIONS_GHC -Wno-orphans #-} -- | -- Module : Streamly.Benchmark.Data.Array.Unboxed.Mut @@ -53,6 +54,10 @@ import Streamly.Benchmark.Common hiding (benchPureSrc) type Stream = MArray.Array +instance NFData (MArray.Array a) where + {-# INLINE rnf #-} + rnf _ = () + ------------------------------------------------------------------------------- -- Benchmark helpers ------------------------------------------------------------------------------- diff --git a/benchmark/Streamly/Benchmark/Data/Fold.hs b/benchmark/Streamly/Benchmark/Data/Fold.hs index 27439c605..b1adc894c 100644 --- a/benchmark/Streamly/Benchmark/Data/Fold.hs +++ b/benchmark/Streamly/Benchmark/Data/Fold.hs @@ -6,16 +6,18 @@ -- Maintainer : streamly@composewell.com {-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE FlexibleInstances #-} {-# LANGUAGE RankNTypes #-} {-# LANGUAGE ScopedTypeVariables #-} {-# OPTIONS_GHC -fno-warn-warnings-deprecations #-} +{-# OPTIONS_GHC -Wno-orphans #-} module Main (main) where import Control.DeepSeq (NFData(..)) import Control.Monad (when) import Control.Monad.IO.Class (MonadIO(..)) -import Data.Functor.Identity (Identity) +import Data.Functor.Identity (Identity(..)) import Data.Map.Strict (Map) import Data.Hashable (Hashable) import Data.HashMap.Strict (HashMap) @@ -27,6 +29,7 @@ import Streamly.Internal.Data.Stream (Stream) import Streamly.Internal.Data.Fold (Fold(..)) import Streamly.Internal.Data.IsMap.HashMap () +import qualified Streamly.Internal.Data.Array.Mut.Type as MArray import qualified Streamly.Internal.Data.Fold as FL import qualified Streamly.Internal.Data.Fold.Extra as FL import qualified Streamly.Internal.Data.Unfold as Unfold @@ -288,6 +291,14 @@ unfoldMany val = moduleName :: String moduleName = "Data.Fold" +instance NFData (MArray.Array a) where + {-# INLINE rnf #-} + rnf _ = () + +instance NFData a => NFData (Stream Identity a) where + {-# INLINE rnf #-} + rnf xs = runIdentity $ Stream.fold (FL.foldl' (\_ x -> rnf x) ()) xs + o_1_space_serial_elimination :: Int -> [Benchmark] o_1_space_serial_elimination value = [ bgroup "elimination" diff --git a/benchmark/Streamly/Benchmark/Data/Stream/Eliminate.hs b/benchmark/Streamly/Benchmark/Data/Stream/Eliminate.hs index 9cb9fb799..e20514c06 100644 --- a/benchmark/Streamly/Benchmark/Data/Stream/Eliminate.hs +++ b/benchmark/Streamly/Benchmark/Data/Stream/Eliminate.hs @@ -6,9 +6,11 @@ {-# LANGUAGE CPP #-} {-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE FlexibleInstances #-} {-# LANGUAGE ScopedTypeVariables #-} {-# LANGUAGE RankNTypes #-} +{-# OPTIONS_GHC -Wno-orphans #-} #ifdef USE_PRELUDE {-# OPTIONS_GHC -Wno-deprecations #-} #endif @@ -252,6 +254,10 @@ o_n_space_elimination_foldable value = -- Stream folds ------------------------------------------------------------------------------- +instance NFData a => NFData (Stream Identity a) where + {-# INLINE rnf #-} + rnf xs = runIdentity $ S.fold (Fold.foldl' (\_ x -> rnf x) ()) xs + {-# INLINE benchPureSink #-} benchPureSink :: NFData b => Int -> String -> (Stream Identity Int -> b) -> Benchmark diff --git a/benchmark/Streamly/Benchmark/Data/Stream/Generate.hs b/benchmark/Streamly/Benchmark/Data/Stream/Generate.hs index f33d6c7e0..16eab0616 100644 --- a/benchmark/Streamly/Benchmark/Data/Stream/Generate.hs +++ b/benchmark/Streamly/Benchmark/Data/Stream/Generate.hs @@ -6,19 +6,23 @@ {-# LANGUAGE CPP #-} {-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE FlexibleInstances #-} {-# LANGUAGE ScopedTypeVariables #-} {-# LANGUAGE RankNTypes #-} +{-# OPTIONS_GHC -Wno-orphans #-} #ifdef USE_PRELUDE {-# OPTIONS_GHC -Wno-deprecations #-} #endif module Stream.Generate (benchmarks) where -import Data.Functor.Identity (Identity) +import Control.DeepSeq (NFData(..)) +import Data.Functor.Identity (Identity(..)) import qualified GHC.Exts as GHC import qualified Stream.Common as Common +import qualified Streamly.Internal.Data.Fold as Fold #ifdef USE_PRELUDE import Streamly.Benchmark.Prelude (sourceFromFoldableM, absTimes) import qualified Streamly.Prelude as S @@ -224,6 +228,10 @@ o_1_space_generation value = ] ] +instance NFData a => NFData (Stream Identity a) where + {-# INLINE rnf #-} + rnf xs = runIdentity $ Stream.fold (Fold.foldl' (\_ x -> rnf x) ()) xs + o_n_heap_generation :: Int -> [Benchmark] o_n_heap_generation value = [ bgroup "buffered" diff --git a/benchmark/Streamly/Benchmark/Data/Stream/Lift.hs b/benchmark/Streamly/Benchmark/Data/Stream/Lift.hs index 98edda35c..fa76f9252 100644 --- a/benchmark/Streamly/Benchmark/Data/Stream/Lift.hs +++ b/benchmark/Streamly/Benchmark/Data/Stream/Lift.hs @@ -17,7 +17,7 @@ module Stream.Lift (benchmarks) where import Control.DeepSeq (NFData(..)) import Control.Monad.Trans.Class (lift) -import Control.Monad.State.Strict (StateT, get, put, MonadState) +import Control.Monad.State.Strict (StateT, get, put) import Data.Functor.Identity (Identity) import Stream.Common (benchIO, sourceUnfoldr, sourceUnfoldrM, benchIOSrc, drain) @@ -107,15 +107,14 @@ iterateStateT n = do {-# INLINE iterateState #-} {-# SPECIALIZE iterateState :: Int -> Stream (StateT Int IO) Int #-} -iterateState :: - MonadState Int m - => Int - -> Stream m Int +iterateState :: Monad m => + Int + -> Stream (StateT Int m) Int iterateState n = do - x <- get + x <- Stream.fromEffect get if x > n then do - put (x - 1) + Stream.fromEffect $ put (x - 1) iterateState n else return x diff --git a/benchmark/Streamly/Benchmark/Data/Stream/Transform.hs b/benchmark/Streamly/Benchmark/Data/Stream/Transform.hs index f17bac3cd..44ace7423 100644 --- a/benchmark/Streamly/Benchmark/Data/Stream/Transform.hs +++ b/benchmark/Streamly/Benchmark/Data/Stream/Transform.hs @@ -6,9 +6,11 @@ {-# LANGUAGE CPP #-} {-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE FlexibleInstances #-} {-# LANGUAGE ScopedTypeVariables #-} {-# LANGUAGE RankNTypes #-} +{-# OPTIONS_GHC -Wno-orphans #-} #ifdef USE_PRELUDE {-# OPTIONS_GHC -Wno-deprecations #-} #endif @@ -26,7 +28,7 @@ module Stream.Transform (benchmarks) where import Control.DeepSeq (NFData(..)) import Control.Monad.IO.Class (MonadIO(..)) -import Data.Functor.Identity (Identity) +import Data.Functor.Identity (Identity(..)) import System.Random (randomRIO) @@ -34,6 +36,7 @@ import qualified Streamly.Internal.Data.Fold as FL import qualified Prelude import qualified Stream.Common as Common +import qualified Streamly.Internal.Data.Fold as Fold import qualified Streamly.Internal.Data.Unfold as Unfold #ifdef USE_PRELUDE import qualified Streamly.Internal.Data.Stream.IsStream as Stream @@ -84,6 +87,10 @@ benchPureSinkIO benchPureSinkIO value name f = bench name $ nfIO $ randomRIO (1, 1) >>= f . sourceUnfoldr value +instance NFData a => NFData (Stream Identity a) where + {-# INLINE rnf #-} + rnf xs = runIdentity $ Stream.fold (Fold.foldl' (\_ x -> rnf x) ()) xs + o_n_space_traversable :: Int -> [Benchmark] o_n_space_traversable value = -- Buffering operations using heap proportional to number of elements. diff --git a/benchmark/Streamly/Benchmark/Unicode/Char.hs b/benchmark/Streamly/Benchmark/Unicode/Char.hs index 776af4e48..fea8724d3 100644 --- a/benchmark/Streamly/Benchmark/Unicode/Char.hs +++ b/benchmark/Streamly/Benchmark/Unicode/Char.hs @@ -1,4 +1,4 @@ -{-# OPTIONS_GHC -Wno-deprecations #-} +{-# OPTIONS_GHC -Wno-deprecations -Wno-orphans #-} -- -- Module : Streamly.Unicode.Char @@ -12,7 +12,7 @@ -- Imports -------------------------------------------------------------------------------- -import Control.DeepSeq (NFData) +import Control.DeepSeq (NFData(..)) import Streamly.Internal.Data.Array (Array) import System.FilePath (dropExtensions, takeFileName) import System.FilePath.Posix (()) @@ -43,7 +43,13 @@ dataDir = "benchmark/Streamly/Benchmark/Unicode/data" dataSetSize :: Int dataSetSize = 1000000 -makeBench :: (NFData a) => (String, a -> IO ()) -> (String, IO a) -> Benchmark +-- Unboxed arrays are fully evaluated. +instance NFData (Array a) where + {-# INLINE rnf #-} + rnf _ = () + +makeBench :: + (String, Array Char -> IO ()) -> (String, IO (Array Char)) -> Benchmark makeBench (implName, func) (dataName, setup) = env setup (bench (implName ++ "/" ++ dataName) . nfIO . func) diff --git a/benchmark/Streamly/Benchmark/Unicode/Utf8.hs b/benchmark/Streamly/Benchmark/Unicode/Utf8.hs index 10acc3972..91a73b7a9 100644 --- a/benchmark/Streamly/Benchmark/Unicode/Utf8.hs +++ b/benchmark/Streamly/Benchmark/Unicode/Utf8.hs @@ -49,7 +49,7 @@ main = runWithCLIOpts defaultStreamSize allBenchmarks allBenchmarks value = [ bgroup moduleName - [ bench "pack" $ nf pack value - , bench "pack + unpack" $ nf packUnpack value + [ bench "pack" $ whnf pack value + , bench "pack + unpack" $ whnf packUnpack value ] ] diff --git a/core/src/Streamly/Internal/Data/Array/Generic.hs b/core/src/Streamly/Internal/Data/Array/Generic.hs index aa660b7fb..f07602aa5 100644 --- a/core/src/Streamly/Internal/Data/Array/Generic.hs +++ b/core/src/Streamly/Internal/Data/Array/Generic.hs @@ -50,7 +50,6 @@ module Streamly.Internal.Data.Array.Generic ) where -import Control.DeepSeq (NFData(..)) import Control.Monad (when, replicateM) import Control.Monad.IO.Class (liftIO, MonadIO) import GHC.Base (MutableArray#, RealWorld) @@ -226,10 +225,6 @@ foldl' f z arr = unsafePerformIO $ D.foldl' f z $ readStreamD arr foldr :: (a -> b -> b) -> b -> Array a -> b foldr f z arr = unsafePerformIO $ D.foldr f z $ readStreamD arr -instance NFData a => NFData (Array a) where - {-# INLINE rnf #-} - rnf = foldl' (\_ x -> rnf x) () - {-# INLINE fold #-} fold :: MonadIO m => Fold m a b -> Array a -> m b fold f arr = D.fold f (readStreamD arr) diff --git a/core/src/Streamly/Internal/Data/Array/Mut/Type.hs b/core/src/Streamly/Internal/Data/Array/Mut/Type.hs index eeaae5be5..b4444eb97 100644 --- a/core/src/Streamly/Internal/Data/Array/Mut/Type.hs +++ b/core/src/Streamly/Internal/Data/Array/Mut/Type.hs @@ -214,7 +214,6 @@ where #include "ArrayMacros.h" #include "MachDeps.h" -import Control.DeepSeq (NFData(..), NFData1(..)) import Control.Monad (when, void) import Control.Monad.IO.Class (MonadIO(..)) import Data.Bits (shiftR, (.|.), (.&.)) @@ -2278,16 +2277,6 @@ cmp arr1 arr2 = -- NFData ------------------------------------------------------------------------------- --- This is an Unbox array, we cannot have unevaluated data in it so this is --- just a no op. -instance NFData (Array a) where - {-# INLINE rnf #-} - rnf Array {} = () - -instance NFData1 Array where - {-# INLINE liftRnf #-} - liftRnf _ Array{} = () - -- | Strip elements which match with predicate from both ends. -- -- /Pre-release/ diff --git a/core/src/Streamly/Internal/Data/Array/Type.hs b/core/src/Streamly/Internal/Data/Array/Type.hs index a5186a333..bf8688aae 100644 --- a/core/src/Streamly/Internal/Data/Array/Type.hs +++ b/core/src/Streamly/Internal/Data/Array/Type.hs @@ -78,7 +78,6 @@ where #include "inline.hs" import Control.Exception (assert) -import Control.DeepSeq (NFData(..), NFData1(..)) import Control.Monad (replicateM) import Control.Monad.IO.Class (MonadIO(..)) import Data.Functor.Identity (Identity(..)) @@ -515,15 +514,6 @@ instance (Unbox a, Eq a) => Eq (Array a) where arr1 == arr2 = (==) EQ $ unsafeInlineIO $! unsafeThaw arr1 `MA.cmp` unsafeThaw arr2 --- Since this is an Unbox array we cannot have unevaluated data in it so --- this is just a no op. -instance NFData (Array a) where - {-# INLINE rnf #-} - rnf Array {} = () - -instance NFData1 Array where - liftRnf _ Array{} = () - instance (Unbox a, Ord a) => Ord (Array a) where {-# INLINE compare #-} compare arr1 arr2 = runIdentity $ diff --git a/core/src/Streamly/Internal/Data/List.hs b/core/src/Streamly/Internal/Data/List.hs index 6a9362a1d..70b081504 100644 --- a/core/src/Streamly/Internal/Data/List.hs +++ b/core/src/Streamly/Internal/Data/List.hs @@ -62,8 +62,6 @@ module Streamly.Internal.Data.List where import Control.Arrow (second) -import Control.DeepSeq (NFData(..)) -import Control.DeepSeq (NFData1(..)) import Data.Functor.Identity (Identity, runIdentity) import GHC.Exts (IsList(..), IsString(..)) import Streamly.Internal.Data.Stream.Type (Stream) @@ -89,7 +87,7 @@ import qualified Streamly.Internal.Data.Stream.Type as Stream -- /Pre-release/ newtype List a = List { toStream :: Stream Identity a } deriving - ( Show, Read, Eq, Ord, NFData , NFData1 + ( Show, Read, Eq, Ord , Semigroup, Monoid, Functor, Foldable , Applicative, Traversable, Monad, IsList) @@ -144,7 +142,7 @@ pattern Cons x xs <- -- @since 0.6.0 newtype ZipList a = ZipList { toZipStream :: ZipStream Identity a } deriving - ( Show, Read, Eq, Ord, NFData , NFData1 + ( Show, Read, Eq, Ord , Semigroup, Monoid, Functor, Foldable , Applicative, Traversable, IsList ) diff --git a/core/src/Streamly/Internal/Data/Parser/ParserD/Type.hs b/core/src/Streamly/Internal/Data/Parser/ParserD/Type.hs index febc505cb..051d4ffff 100644 --- a/core/src/Streamly/Internal/Data/Parser/ParserD/Type.hs +++ b/core/src/Streamly/Internal/Data/Parser/ParserD/Type.hs @@ -211,8 +211,6 @@ import Control.Applicative (Alternative(..), liftA2) import Control.Exception (Exception(..)) import Control.Monad (MonadPlus(..), (>=>)) import Control.Monad.IO.Class (MonadIO, liftIO) -import Control.Monad.Reader.Class (MonadReader, ask, local) -import Control.Monad.State.Class (MonadState, get, put) import Data.Bifunctor (Bifunctor(..)) import Fusion.Plugin.Types (Fuse(..)) import Streamly.Internal.Data.Fold.Type (Fold(..), toList) @@ -1481,23 +1479,6 @@ instance Monad m => MonadPlus (Parser a m) where {-# INLINE mplus #-} mplus = alt -instance (Monad m, MonadReader r m) => MonadReader r (Parser a m) where - {-# INLINE ask #-} - ask = fromEffect ask - - {-# INLINE local #-} - local f (Parser step init' extract) = - Parser ((local f .) . step) - (local f init') - (local f . extract) - -instance (Monad m, MonadState s m) => MonadState s (Parser a m) where - {-# INLINE get #-} - get = fromEffect get - - {-# INLINE put #-} - put = fromEffect . put - instance (Monad m, MonadIO m) => MonadIO (Parser a m) where {-# INLINE liftIO #-} liftIO = fromEffect . liftIO diff --git a/core/src/Streamly/Internal/Data/Parser/ParserK/Type.hs b/core/src/Streamly/Internal/Data/Parser/ParserK/Type.hs index 7574bce90..0a32a2a79 100644 --- a/core/src/Streamly/Internal/Data/Parser/ParserK/Type.hs +++ b/core/src/Streamly/Internal/Data/Parser/ParserK/Type.hs @@ -32,10 +32,8 @@ where import Control.Applicative (Alternative(..), liftA2) import Control.Monad (MonadPlus(..), ap) -import Control.Monad.Catch (MonadCatch, MonadThrow(..)) import Control.Monad.IO.Class (MonadIO, liftIO) -import Control.Monad.Reader.Class (MonadReader, ask, local) -import Control.Monad.State.Class (MonadState, get, put) +-- import Control.Monad.Trans.Class (MonadTrans(lift)) import qualified Control.Monad.Fail as Fail -- | The intermediate result of running a parser step. The parser driver may @@ -248,23 +246,7 @@ instance Monad m => Fail.MonadFail (Parser a m) where {-# INLINE fail #-} fail = die -instance (MonadThrow m, MonadReader r m, MonadCatch m) => - MonadReader r (Parser a m) where - - {-# INLINE ask #-} - ask = fromEffect ask - - {-# INLINE local #-} - local f p = MkParser $ \n st k -> local f $ runParser p n st k - -instance (MonadThrow m, MonadState s m) => MonadState s (Parser a m) where - {-# INLINE get #-} - get = fromEffect get - - {-# INLINE put #-} - put = fromEffect . put - -instance (MonadThrow m, MonadIO m) => MonadIO (Parser a m) where +instance MonadIO m => MonadIO (Parser a m) where {-# INLINE liftIO #-} liftIO = fromEffect . liftIO @@ -324,3 +306,9 @@ instance Monad m => MonadPlus (Parser a m) where {-# INLINE mplus #-} mplus = (<|>) + +{- +instance MonadTrans (Parser a) where + {-# INLINE lift #-} + lift = fromEffect +-} diff --git a/core/src/Streamly/Internal/Data/Stream/StreamK.hs b/core/src/Streamly/Internal/Data/Stream/StreamK.hs index f69696a56..6de43cc46 100644 --- a/core/src/Streamly/Internal/Data/Stream/StreamK.hs +++ b/core/src/Streamly/Internal/Data/Stream/StreamK.hs @@ -171,7 +171,6 @@ module Streamly.Internal.Data.Stream.StreamK -- * Utilities , consM - , withLocal , mfix ) where diff --git a/core/src/Streamly/Internal/Data/Stream/StreamK/Type.hs b/core/src/Streamly/Internal/Data/Stream/StreamK/Type.hs index 36a712287..e10c9c0b7 100644 --- a/core/src/Streamly/Internal/Data/Stream/StreamK/Type.hs +++ b/core/src/Streamly/Internal/Data/Stream/StreamK/Type.hs @@ -99,20 +99,18 @@ module Streamly.Internal.Data.Stream.StreamK.Type , interleaveMin -- * Reader - , withLocal , evalStateT , liftInner ) where import Control.Monad (ap, (>=>)) -import Control.Monad.Reader.Class (MonadReader(..)) -import Control.Monad.State.Strict (StateT) import Control.Monad.Trans.Class (MonadTrans(lift)) +import Control.Monad.Trans.State.Strict (StateT) import Data.Function (fix) import Streamly.Internal.Data.SVar.Type (State, adaptState, defState) -import qualified Control.Monad.State.Strict as State +import qualified Control.Monad.Trans.State.Strict as State import qualified Prelude import Prelude hiding @@ -1187,18 +1185,6 @@ interleaveMin m1 m2 = mkStream $ \st yld _ stp -> do yieldk a r = yld a (interleaveMin m2 r) foldStream st yieldk single stop m1 ------------------------------------------------------------------------------- --- MonadReader ------------------------------------------------------------------------------- - -{-# INLINABLE withLocal #-} -withLocal :: MonadReader r m => (r -> r) -> Stream m a -> Stream m a -withLocal f m = - mkStream $ \st yld sng stp -> - let single = local f . sng - yieldk a r = local f $ yld a (withLocal f r) - in foldStream st yieldk single (local f stp) m - ------------------------------------------------------------------------------- -- Generation ------------------------------------------------------------------------------- diff --git a/core/src/Streamly/Internal/Data/Stream/Transform.hs b/core/src/Streamly/Internal/Data/Stream/Transform.hs index b05a4d671..75c4db4e7 100644 --- a/core/src/Streamly/Internal/Data/Stream/Transform.hs +++ b/core/src/Streamly/Internal/Data/Stream/Transform.hs @@ -169,6 +169,7 @@ import Prelude hiding -- -- $setup -- >>> :m +-- >>> :set -package mtl -- >>> import Control.Concurrent (threadDelay) -- >>> import Control.Monad.IO.Class (MonadIO (liftIO)) -- >>> import Control.Monad.Trans (lift) diff --git a/core/src/Streamly/Internal/Data/Stream/Type.hs b/core/src/Streamly/Internal/Data/Stream/Type.hs index 9d15a096e..94e00f910 100644 --- a/core/src/Streamly/Internal/Data/Stream/Type.hs +++ b/core/src/Streamly/Internal/Data/Stream/Type.hs @@ -41,11 +41,8 @@ where #include "inline.hs" import Control.Applicative (liftA2) -import Control.DeepSeq (NFData(..), NFData1(..)) import Control.Monad.Catch (MonadThrow, throwM) import Control.Monad.IO.Class (MonadIO(..)) -import Control.Monad.Reader.Class (MonadReader(..)) -import Control.Monad.State.Class (MonadState(..)) import Control.Monad.Trans.Class (MonadTrans(lift)) import Data.Foldable (Foldable(foldl'), fold) import Data.Functor.Identity (Identity(..), runIdentity) @@ -241,33 +238,6 @@ instance (MonadIO m) => MonadIO (Stream m) where instance (MonadThrow m) => MonadThrow (Stream m) where throwM = lift . throwM -instance (MonadReader r m) => MonadReader r (Stream m) where - ask = lift ask - - local f (Stream m) = Stream $ K.withLocal f m - -instance (MonadState s m) => MonadState s (Stream m) where - {-# INLINE get #-} - get = lift get - - {-# INLINE put #-} - put x = lift (put x) - - {-# INLINE state #-} - state k = lift (state k) - ------------------------------------------------------------------------------- --- NFData ------------------------------------------------------------------------------- - -instance NFData a => NFData (Stream Identity a) where - {-# INLINE rnf #-} - rnf (Stream xs) = runIdentity $ P.foldl' (\_ x -> rnf x) () xs - -instance NFData1 (Stream Identity) where - {-# INLINE liftRnf #-} - liftRnf f (Stream xs) = runIdentity $ P.foldl' (\_ x -> f x) () xs - ------------------------------------------------------------------------------ -- Lists ------------------------------------------------------------------------------ diff --git a/core/src/Streamly/Internal/Data/Stream/Zip.hs b/core/src/Streamly/Internal/Data/Stream/Zip.hs index 8463b18f0..dfe5f3bcd 100644 --- a/core/src/Streamly/Internal/Data/Stream/Zip.hs +++ b/core/src/Streamly/Internal/Data/Stream/Zip.hs @@ -24,7 +24,6 @@ module Streamly.Internal.Data.Stream.Zip ) where -import Control.DeepSeq (NFData(..), NFData1(..)) import Data.Functor.Identity (Identity(..)) import GHC.Exts (IsList(..), IsString(..)) import Streamly.Internal.Data.Stream.Type (Stream) @@ -62,8 +61,6 @@ import qualified Streamly.Internal.Data.Stream as Stream newtype ZipStream m a = ZipStream {getZipStream :: Stream m a} deriving (Functor, Semigroup, Monoid) -deriving instance NFData a => NFData (ZipStream Identity a) -deriving instance NFData1 (ZipStream Identity) deriving instance IsList (ZipStream Identity a) deriving instance (a ~ Char) => IsString (ZipStream Identity a) deriving instance Eq a => Eq (ZipStream Identity a) diff --git a/core/streamly-core.cabal b/core/streamly-core.cabal index a73d8225a..500934ced 100644 --- a/core/streamly-core.cabal +++ b/core/streamly-core.cabal @@ -237,7 +237,6 @@ library , Streamly.Internal.Control.Exception , Streamly.Internal.Control.Monad , Streamly.Internal.Control.ForkIO - , Streamly.Internal.Data.Cont , Streamly.Internal.System.IO -- streamly-strict-data @@ -410,10 +409,8 @@ library -- depending on doctest is a common example) can -- depend on streamly. base >= 4.12 && < 4.18 - , deepseq >= 1.4.4 && < 1.5 , exceptions >= 0.8.0 && < 0.11 , ghc-prim >= 0.5.3 && < 0.10 - , mtl >= 2.2.2 && < 2.4 , transformers >= 0.5.5 && < 0.7 -- streamly-unicode-core diff --git a/hie.yaml b/hie.yaml index 5bfc828e3..9e2bf8dbd 100644 --- a/hie.yaml +++ b/hie.yaml @@ -70,6 +70,8 @@ cradle: component: "bench:Unicode.Char" - path: "./benchmark/Streamly/Benchmark/Unicode/Stream.hs" component: "bench:Unicode.Stream" + - path: "./benchmark/Streamly/Benchmark/Unicode/Utf8.hs" + component: "bench:Unicode.Utf8" - path: "./benchmark/lib/" component: "lib:streamly-benchmarks" - path: "./benchmark/Streamly/Benchmark/Data/Fold/Window.hs" diff --git a/src/Streamly/Data/Array/Foreign.hs b/src/Streamly/Data/Array/Foreign.hs index 3d8945f87..ee3aae03f 100644 --- a/src/Streamly/Data/Array/Foreign.hs +++ b/src/Streamly/Data/Array/Foreign.hs @@ -1,3 +1,4 @@ +{-# OPTIONS_GHC -Wno-orphans #-} #include "inline.hs" -- | @@ -93,6 +94,7 @@ module Streamly.Data.Array.Foreign ) where +import Control.DeepSeq (NFData(..), NFData1(..)) import Streamly.Internal.Data.Array as A -- $setup @@ -104,3 +106,14 @@ import Streamly.Internal.Data.Array as A -- >>> import Streamly.Data.Array (Array) -- >>> import qualified Streamly.Internal.Data.Stream.IsStream as Stream -- >>> import qualified Streamly.Data.Array as Array + +-- Orphan instances for backward compatibility +-- Since this is an Unbox array we cannot have unevaluated data in it so +-- this is just a no op. + +instance NFData (Array a) where + {-# INLINE rnf #-} + rnf _ = () + +instance NFData1 Array where + liftRnf _ _ = () diff --git a/core/src/Streamly/Internal/Data/Cont.hs b/src/Streamly/Internal/Data/Cont.hs similarity index 100% rename from core/src/Streamly/Internal/Data/Cont.hs rename to src/Streamly/Internal/Data/Cont.hs diff --git a/src/Streamly/Internal/Data/Stream/Ahead.hs b/src/Streamly/Internal/Data/Stream/Ahead.hs index ebfd6c195..88a8c6c03 100644 --- a/src/Streamly/Internal/Data/Stream/Ahead.hs +++ b/src/Streamly/Internal/Data/Stream/Ahead.hs @@ -52,7 +52,7 @@ import Streamly.Internal.Data.Stream.StreamK.Type (Stream) import qualified Streamly.Internal.Data.Stream.StreamK.Type as K (foldStreamShared, cons, mkStream, foldStream, fromEffect - , nil, concatMapWith, fromPure, bindWith, withLocal) + , nil, concatMapWith, fromPure, bindWith) import qualified Streamly.Internal.Data.Stream.StreamD.Type as D (mapM, fromStreamK, toStreamK) import qualified Streamly.Internal.Data.Stream as Stream (toStreamK) @@ -74,6 +74,14 @@ import Prelude hiding (map) -- return n -- IO Int -- :} +{-# INLINABLE withLocal #-} +withLocal :: MonadReader r m => (r -> r) -> Stream m a -> Stream m a +withLocal f m = + K.mkStream $ \st yld sng stp -> + let single = local f . sng + yieldk a r = local f $ yld a (withLocal f r) + in K.foldStream st yieldk single (local f stp) m + ------------------------------------------------------------------------------- -- Ahead ------------------------------------------------------------------------------- diff --git a/src/Streamly/Internal/Data/Stream/Async.hs b/src/Streamly/Internal/Data/Stream/Async.hs index 20742a864..6caa3e2f0 100644 --- a/src/Streamly/Internal/Data/Stream/Async.hs +++ b/src/Streamly/Internal/Data/Stream/Async.hs @@ -63,7 +63,7 @@ import Streamly.Internal.Data.Stream.SVar.Generate (fromSVar, fromSVarD) import qualified Streamly.Internal.Data.Stream.StreamK.Type as K (foldStreamShared, mkStream, foldStream, fromEffect - , nil, concatMapWith, fromPure, bindWith, withLocal) + , nil, concatMapWith, fromPure, bindWith) import qualified Streamly.Internal.Data.Stream.StreamD.Type as D (Stream(..), Step(..), mapM, toStreamK, fromStreamK) import qualified Streamly.Internal.Data.Stream as Stream (toStreamK) @@ -84,6 +84,14 @@ import Streamly.Internal.Data.SVar -- :} -- +{-# INLINABLE withLocal #-} +withLocal :: MonadReader r m => (r -> r) -> Stream m a -> Stream m a +withLocal f m = + K.mkStream $ \st yld sng stp -> + let single = local f . sng + yieldk a r = local f $ yld a (withLocal f r) + in K.foldStream st yieldk single (local f stp) m + ------------------------------------------------------------------------------- -- Async ------------------------------------------------------------------------------- diff --git a/src/Streamly/Internal/Data/Stream/Instances.hs b/src/Streamly/Internal/Data/Stream/Instances.hs index 200058c75..cc2418226 100644 --- a/src/Streamly/Internal/Data/Stream/Instances.hs +++ b/src/Streamly/Internal/Data/Stream/Instances.hs @@ -33,7 +33,7 @@ instance (MonadError e m CONSTRAINT) => MonadError e (STREAM m) where { \ \ instance (MonadReader r m CONSTRAINT) => MonadReader r (STREAM m) where { \ ask = lift ask; \ - local f (STREAM m) = STREAM $ K.withLocal f m }; \ + local f (STREAM m) = STREAM $ withLocal f m }; \ \ instance (MonadState s m CONSTRAINT) => MonadState s (STREAM m) where { \ {-# INLINE get #-}; \ diff --git a/src/Streamly/Internal/Data/Stream/IsStream.hs b/src/Streamly/Internal/Data/Stream/IsStream.hs index cf7d92531..eddd756cb 100644 --- a/src/Streamly/Internal/Data/Stream/IsStream.hs +++ b/src/Streamly/Internal/Data/Stream/IsStream.hs @@ -1,4 +1,5 @@ -{-# OPTIONS_GHC -Wno-deprecations #-} +{-# OPTIONS_GHC -Wno-deprecations -Wno-orphans #-} +{-# LANGUAGE StandaloneDeriving #-} -- | -- Module : Streamly.Internal.Data.Stream.IsStream @@ -25,6 +26,10 @@ module Streamly.Internal.Data.Stream.IsStream {-# DEPRECATED "Please use \"Stre ) where +import Control.DeepSeq (NFData(..), NFData1(..)) +import Data.Functor.Identity (Identity(..)) +import Streamly.Internal.Data.Stream.Zip (ZipStream(..)) + import Streamly.Internal.Data.Stream.IsStream.Top import Streamly.Internal.Data.Stream.IsStream.Eliminate import Streamly.Internal.Data.Stream.IsStream.Exception @@ -36,3 +41,6 @@ import Streamly.Internal.Data.Stream.IsStream.Transform import Streamly.Internal.Data.Stream.IsStream.Type hiding (cmpBy, drain, eqBy, foldl', fold, toList, toStream , fromEffect, fromPure, repeat) + +deriving instance NFData a => NFData (ZipStream Identity a) +deriving instance NFData1 (ZipStream Identity) diff --git a/src/Streamly/Internal/Data/Stream/Parallel.hs b/src/Streamly/Internal/Data/Stream/Parallel.hs index 5cf5199d7..b3bdc43b1 100644 --- a/src/Streamly/Internal/Data/Stream/Parallel.hs +++ b/src/Streamly/Internal/Data/Stream/Parallel.hs @@ -71,7 +71,7 @@ import Streamly.Internal.Data.Stream.Type (Stream) import qualified Data.Set as Set import qualified Streamly.Internal.Data.Stream.StreamK.Type as K (Stream, foldStreamShared, mkStream, foldStream, fromEffect - , nil, concatMapWith, fromPure, bindWith, withLocal) + , nil, concatMapWith, fromPure, bindWith) import qualified Streamly.Internal.Data.Stream.StreamD.Type as D (Stream(..), mapM, toStreamK, fromStreamK) import qualified Streamly.Internal.Data.Stream.SVar.Generate as SVar @@ -96,6 +96,14 @@ import Prelude hiding (map) -- return n -- IO Int -- :} +{-# INLINABLE withLocal #-} +withLocal :: MonadReader r m => (r -> r) -> K.Stream m a -> K.Stream m a +withLocal f m = + K.mkStream $ \st yld sng stp -> + let single = local f . sng + yieldk a r = local f $ yld a (withLocal f r) + in K.foldStream st yieldk single (local f stp) m + ------------------------------------------------------------------------------- -- Parallel ------------------------------------------------------------------------------- diff --git a/src/Streamly/Internal/Data/Stream/Serial.hs b/src/Streamly/Internal/Data/Stream/Serial.hs index 27bc5693f..c6dafa8c0 100644 --- a/src/Streamly/Internal/Data/Stream/Serial.hs +++ b/src/Streamly/Internal/Data/Stream/Serial.hs @@ -1,4 +1,5 @@ {-# LANGUAGE UndecidableInstances #-} +{-# OPTIONS_GHC -Wno-orphans #-} -- | -- Module : Streamly.Internal.Data.Stream.Serial @@ -65,13 +66,15 @@ import Streamly.Internal.BaseCompat ((#.)) import Streamly.Internal.Data.Maybe.Strict (Maybe'(..), toMaybe) import Streamly.Data.Stream (Stream) +import qualified Streamly.Data.Fold as Fold import qualified Streamly.Data.Stream as Stream +import qualified Streamly.Internal.Data.Stream as Stream (toStreamK, fromStreamK) import qualified Streamly.Internal.Data.Stream.Common as P import qualified Streamly.Internal.Data.Stream.StreamD as D (fromStreamK, toStreamK, mapM) import qualified Streamly.Internal.Data.Stream.StreamK.Type as K - (Stream, cons, consM, nil, concatMapWith, fromPure, bindWith - , withLocal, interleave, interleaveFst, interleaveMin) + (Stream, mkStream, foldStream, cons, consM, nil, concatMapWith, fromPure + , bindWith, interleave, interleaveFst, interleaveMin) import Prelude hiding (map, mapM, repeat, filter) @@ -83,6 +86,45 @@ import Prelude hiding (map, mapM, repeat, filter) -- >>> import qualified Streamly.Data.Stream as Stream -- >>> import qualified Streamly.Prelude as IsStream +{-# INLINABLE withLocal #-} +withLocal :: MonadReader r m => (r -> r) -> K.Stream m a -> K.Stream m a +withLocal f m = + K.mkStream $ \st yld sng stp -> + let single = local f . sng + yieldk a r = local f $ yld a (withLocal f r) + in K.foldStream st yieldk single (local f stp) m + +------------------------------------------------------------------------------ +-- mtl orphan instances +------------------------------------------------------------------------------ + +instance (MonadReader r m) => MonadReader r (Stream m) where + ask = lift ask + + local f m = Stream.fromStreamK $ withLocal f (Stream.toStreamK m) + +instance (MonadState s m) => MonadState s (Stream m) where + {-# INLINE get #-} + get = lift get + + {-# INLINE put #-} + put x = lift (put x) + + {-# INLINE state #-} + state k = lift (state k) + +------------------------------------------------------------------------------ +-- NFData - orphan instances +------------------------------------------------------------------------------ + +instance NFData a => NFData (Stream Identity a) where + {-# INLINE rnf #-} + rnf xs = runIdentity $ Stream.fold (Fold.foldl' (\_ x -> rnf x) ()) xs + +instance NFData1 (Stream Identity) where + {-# INLINE liftRnf #-} + liftRnf f xs = runIdentity $ Stream.fold (Fold.foldl' (\_ x -> f x) ()) xs + ------------------------------------------------------------------------------ -- SerialT ------------------------------------------------------------------------------ diff --git a/src/Streamly/Internal/Unicode/Utf8.hs b/src/Streamly/Internal/Unicode/Utf8.hs index a1a1d07c1..1f9877a12 100644 --- a/src/Streamly/Internal/Unicode/Utf8.hs +++ b/src/Streamly/Internal/Unicode/Utf8.hs @@ -27,7 +27,6 @@ where -- Imports -------------------------------------------------------------------------------- -import Control.DeepSeq (NFData) import Data.Word (Word8) import Streamly.Data.Array (Array) import System.IO.Unsafe (unsafePerformIO) @@ -45,9 +44,7 @@ import qualified Streamly.Internal.Unicode.Stream as Unicode -------------------------------------------------------------------------------- -- | A space efficient, packed, unboxed Unicode container. -newtype Utf8 = - Utf8 (Array Word8) - deriving (NFData) +newtype Utf8 = Utf8 (Array Word8) -------------------------------------------------------------------------------- -- Functions diff --git a/streamly.cabal b/streamly.cabal index 187f55e25..84b94c353 100644 --- a/streamly.cabal +++ b/streamly.cabal @@ -342,6 +342,7 @@ library Streamly.Internal.Data.IsMap , Streamly.Internal.Data.IsMap.HashMap + , Streamly.Internal.Data.Cont -- streamly-concurrent , Streamly.Internal.Control.Concurrent