@@ -22,19 +22,8 @@
22-- better performance compared to @[a]@. Standard list, string and list
22-- better performance compared to @[a]@. Standard list, string and list
23-- comprehension syntax can be used with the 'List' type by enabling
23-- comprehension syntax can be used with the 'List' type by enabling
24-- 'OverloadedLists', 'OverloadedStrings' and 'MonadComprehensions' GHC
24-- 'OverloadedLists', 'OverloadedStrings' and 'MonadComprehensions' GHC
25−-- extensions. If you want to replace streamly lists with standard lists, all
26−-- you need to do is import these definitions:
30−-- pattern Nil <- [] where Nil = []
31−-- pattern Cons x xs = x : xs
33−-- {-\# COMPLETE Cons, Nil #-}
36−-- Other than that there would be a slight difference in the 'Show' and
25+-- extensions. There would be a slight difference in the 'Show' and 'Read'
37−-- 'Read' strings.
26+-- strings of streamly list as compared to regular lists.
39-- Conversion to stream types is free, any stream combinator can be used on
28-- Conversion to stream types is free, any stream combinator can be used on
40-- lists by converting them to streams. However, for convenience, this module
29-- lists by converting them to streams. However, for convenience, this module
@@ -45,9 +34,23 @@
45-- List $ S.map (+ 1) $ toSerial (1 \`Cons\` Nil)
34-- List $ S.map (+ 1) $ toSerial (1 \`Cons\` Nil)
37+-- To convert a 'List' to regular lists, you can use any of the following:
39+-- * @toList . toSerial@ and @toSerial . fromList@
48−-- 'Data.Foldable.toList' from 'Foldable' and 'GHC.Exts.toList' and
40+-- * 'Data.Foldable.toList' from "Data.Foldable"
49−-- 'GHC.Exts.fromList' from 'IsList' can also be used to convert to and from
41+-- * 'GHC.Exts.toList' and 'GHC.Exts.fromList' from 'IsList' in "GHC.Exts"
50−-- standard lists.
42+--
43+-- If you have made use of 'Nil' and 'Cons' constructors in the code and you
44+-- want to replace streamly lists with standard lists, all you need to do is
45+-- import these definitions:
49+-- pattern Nil <- [] where Nil = []
50+-- pattern Cons x xs = x : xs
52+-- {-\# COMPLETE Cons, Nil #-}
52-- See <src/docs/streamly-vs-lists.md> for more details and
55-- See <src/docs/streamly-vs-lists.md> for more details and
53-- <src/test/PureStreams.hs> for comprehensive usage examples.
56-- <src/test/PureStreams.hs> for comprehensive usage examples.
@@ -61,6 +64,8 @@ module Streamly.List
61 , pattern Nil
64 , pattern Nil
62 , pattern Cons
65 , pattern Cons
67+ -- XXX we may want to use rebindable syntax for variants instead of using
68+ -- different types (applicative do and apWith).
64 , ZipList (..)
69 , ZipList (..)
65 , fromZipList
70 , fromZipList
66 , toZipList
71 , toZipList
@@ -84,9 +89,16 @@ import qualified Streamly.Streams.StreamK as K
84-- using a stream type the programmer needs to specify the Monad otherwise the
89-- using a stream type the programmer needs to specify the Monad otherwise the
85-- type remains ambiguous.
90-- type remains ambiguous.
92+-- XXX once we separate consM from IsStream or remove the MonadIO and
93+-- MonadBaseControlIO dependency from it, then we can make this an instance of
94+-- IsStream and use the regular polymorphic functions on Lists as well. Once
95+-- that happens we can change the Show and Read instances as well to use "1 >:
96+-- 2 >: nil" etc. or should we use a separate constructor indicating the "List"
97+-- type ":>" for better inference?
87-- | @List a@ is a replacement for @[a]@.
99-- | @List a@ is a replacement for @[a]@.
89−-- @since 0.5.3
101+-- @since 0.6.0
90newtype List a = List { toSerial :: SerialT Identity a }
102newtype List a = List { toSerial :: SerialT Identity a }
91 deriving (Show, Read, Eq, Ord, NFData, NFData1
103 deriving (Show, Read, Eq, Ord, NFData, NFData1
92 , Semigroup, Monoid, Functor, Foldable
104 , Semigroup, Monoid, Functor, Foldable
@@ -108,10 +120,16 @@ instance IsList (List a) where
108-- Patterns
120-- Patterns
109------------------------------------------------------------------------------
121------------------------------------------------------------------------------
123+-- Note: When using the OverloadedLists extension we should be able to pattern
124+-- match using the regular list contructors. OverloadedLists uses 'toList' to
125+-- perform the pattern match, it should not be too bad as it works lazily in
126+-- the Identity monad. We need these patterns only when not using that
111-- | An empty list constructor and pattern that matches an empty 'List'.
129-- | An empty list constructor and pattern that matches an empty 'List'.
112-- Corresponds to '[]' for Haskell lists.
130-- Corresponds to '[]' for Haskell lists.
114−-- @since 0.5.3
132+-- @since 0.6.0
115pattern Nil :: List a
133pattern Nil :: List a
116pattern Nil <- (runIdentity . K.null . toSerial -> True) where
134pattern Nil <- (runIdentity . K.null . toSerial -> True) where
117 Nil = List K.nil
135 Nil = List K.nil
@@ -121,7 +139,7 @@ infixr 5 `Cons`
121-- | A list constructor and pattern that deconstructs a 'List' into its head
139-- | A list constructor and pattern that deconstructs a 'List' into its head
122-- and tail. Corresponds to ':' for Haskell lists.
140-- and tail. Corresponds to ':' for Haskell lists.
124−-- @since 0.5.3
142+-- @since 0.6.0
125pattern Cons :: a -> List a -> List a
143pattern Cons :: a -> List a -> List a
126pattern Cons x xs <-
144pattern Cons x xs <-
127 (fmap (second List) . runIdentity . K.uncons . toSerial
145 (fmap (second List) . runIdentity . K.uncons . toSerial
@@ -139,7 +157,7 @@ pattern Cons x xs <-
139-- | Just like 'List' except that it has a zipping 'Applicative' instance
157-- | Just like 'List' except that it has a zipping 'Applicative' instance
140-- and no 'Monad' instance.
158-- and no 'Monad' instance.
142−-- @since 0.5.3
160+-- @since 0.6.0
143newtype ZipList a = ZipList { toZipSerial :: ZipSerialM Identity a }
161newtype ZipList a = ZipList { toZipSerial :: ZipSerialM Identity a }
144 deriving (Show, Read, Eq, Ord, NFData, NFData1
162 deriving (Show, Read, Eq, Ord, NFData, NFData1
145 , Semigroup, Monoid, Functor, Foldable
163 , Semigroup, Monoid, Functor, Foldable
@@ -159,12 +177,12 @@ instance IsList (ZipList a) where
160-- | Convert a 'ZipList' to a regular 'List'
178-- | Convert a 'ZipList' to a regular 'List'
162−-- @since 0.5.3
180+-- @since 0.6.0
163fromZipList :: ZipList a -> List a
181fromZipList :: ZipList a -> List a
164fromZipList = List . K.adapt . toZipSerial
182fromZipList = List . K.adapt . toZipSerial
166-- | Convert a regular 'List' to a 'ZipList'
184-- | Convert a regular 'List' to a 'ZipList'
168−-- @since 0.5.3
186+-- @since 0.6.0
169toZipList :: List a -> ZipList a
187toZipList :: List a -> ZipList a
170toZipList = ZipList . K.adapt . toSerial
188toZipList = ZipList . K.adapt . toSerial