@@ -1,3 +1,10 @@
1+{-# OPTIONS_GHC -Wno-deprecations #-}
5+{-# OPTIONS_GHC -ddump-simpl -ddump-to-file -dsuppress-all #-}
2-- Module : Streamly.Benchmark.Data.Parser
9-- Module : Streamly.Benchmark.Data.Parser
3-- Copyright : (c) 2020 Composewell Technologies
10-- Copyright : (c) 2020 Composewell Technologies
@@ -7,39 +14,42 @@
8{-# LANGUAGE CPP #-}
15{-# LANGUAGE CPP #-}
9{-# LANGUAGE FlexibleContexts #-}
16{-# LANGUAGE FlexibleContexts #-}
17+{-# LANGUAGE ScopedTypeVariables #-}
18+{-# OPTIONS_GHC -Wno-orphans #-}
11module Main
20module Main
25+import Control.Applicative ((<|>))
16import Control.DeepSeq (NFData(..))
26import Control.DeepSeq (NFData(..))
17−import Control.Monad.Catch (MonadCatch)
27+import Data.Function ((&))
18−import Data.Foldable (asum)
19import Data.Functor (($>))
28import Data.Functor (($>))
20−import Data.Maybe (fromMaybe)
21import Data.Monoid (Sum(..))
29import Data.Monoid (Sum(..))
22import GHC.Magic (inline)
30import GHC.Magic (inline)
23import GHC.Magic (noinline)
31import GHC.Magic (noinline)
24import System.IO (Handle)
32import System.IO (Handle)
25import System.Random (randomRIO)
33import System.Random (randomRIO)
34+import Streamly.Internal.Data.Fold (Fold(..))
35+import Streamly.Internal.Data.Parser
36+ (ParseError(..), Parser(..), Initial(..), Step(..))
37+import Streamly.Internal.Data.Stream (Stream)
26−import Prelude
38+import Prelude hiding
27− hiding (any, all, take, sequence, sequence_, sequenceA, takeWhile)
39+ (any, all, take, sequence, sequence_, sequenceA, takeWhile, dropWhile, span)
29−import qualified Data.Traversable as TR
30−import qualified Data.Foldable as F
31import qualified Control.Applicative as AP
41import qualified Control.Applicative as AP
42+import qualified Data.Foldable as F
43+import qualified Data.Traversable as TR
32import qualified Streamly.FileSystem.Handle as Handle
44import qualified Streamly.FileSystem.Handle as Handle
33−import qualified Streamly.Prelude as S
45+import qualified Streamly.Internal.Data.Array as Array
34−import qualified Streamly.Internal.Data.Array.Foreign as Array
35−import qualified Streamly.Internal.Data.Fold as FL
46+import qualified Streamly.Internal.Data.Fold as Fold
36import qualified Streamly.Internal.Data.Parser as PR
47import qualified Streamly.Internal.Data.Parser as PR
37−import qualified Streamly.Internal.Data.Stream.IsStream as IP
48+import qualified Streamly.Data.Stream as Stream
38import qualified Streamly.Internal.Data.Producer as Producer
49import qualified Streamly.Internal.Data.Producer as Producer
39−import qualified Streamly.Internal.Data.Producer.Source as Source
50+import qualified Streamly.Internal.Data.Stream as Stream
41−import Gauge hiding (env)
52+import Test.Tasty.Bench hiding (env)
42−import Streamly.Prelude (SerialT)
43import Streamly.Benchmark.Common
53import Streamly.Benchmark.Common
44import Streamly.Benchmark.Common.Handle
54import Streamly.Benchmark.Common.Handle
@@ -50,19 +60,59 @@ import Streamly.Benchmark.Common.Handle
50-- XXX these can be moved to the common module
60-- XXX these can be moved to the common module
52{-# INLINE sourceUnfoldrM #-}
62{-# INLINE sourceUnfoldrM #-}
53−sourceUnfoldrM :: (S.IsStream t, S.MonadAsync m) => Int -> Int -> t m Int
63+sourceUnfoldrM :: Monad m => Int -> Int -> Stream m Int
54−sourceUnfoldrM value n = S.unfoldrM step n
64+sourceUnfoldrM value n = Stream.unfoldrM step n
56 step cnt =
66 step cnt =
57 if cnt > n + value
67 if cnt > n + value
58 then return Nothing
68 then return Nothing
59 else return (Just (cnt, cnt + 1))
69 else return (Just (cnt, cnt + 1))
71+-- | Generates something like this: { { \{ \{ } }. The stream consists of
72+-- three parts, the first part is contains a sequence of `{`. The second part
73+-- contains a sequence pf escaped values `\{`. The third part contains a
75+{-# INLINE sourceEscapedFrames #-}
76+sourceEscapedFrames ::
81+sourceEscapedFrames value n = Stream.unfoldrM step n
87+ value1 = value `div` 4
90+ | cnt > 4 * value1 = return Nothing
91+ | cnt <= value1 = return $ Just (cbOpen, cnt + 1)
92+ | cnt > 3 * value1 = return $ Just (cbClose, cnt + 1)
96+ $ if (cnt - value1) `mod` 2 == 1
98+ else (cbOpen, cnt + 1)
100+{-# INLINE benchIOSrc #-}
103+ => (Int -> Int -> Stream IO a)
106+ -> (Stream IO a -> IO b)
108+benchIOSrc src value name f =
109+ bench name $ nfIO $ randomRIO (1,1) >>= f . src value
61-- | Takes a fold method, and uses it with a default source.
111-- | Takes a fold method, and uses it with a default source.
62{-# INLINE benchIOSink #-}
112{-# INLINE benchIOSink #-}
63benchIOSink
113benchIOSink
64− :: (S.IsStream t, NFData b)
114+ :: NFData b
65− => Int -> String -> (t IO Int -> IO b) -> Benchmark
115+ => Int -> String -> (Stream IO Int -> IO b) -> Benchmark
66benchIOSink value name f =
116benchIOSink value name f =
67 bench name $ nfIO $ randomRIO (1,1) >>= f . sourceUnfoldrM value
117 bench name $ nfIO $ randomRIO (1,1) >>= f . sourceUnfoldrM value
@@ -70,199 +120,452 @@ benchIOSink value name f =
70-- Parsers
120-- Parsers
71-------------------------------------------------------------------------------
121-------------------------------------------------------------------------------
74−next :: MonadCatch m => Int -> SerialT m Int -> m (Maybe Int)
75−next value = IP.parse p
80− Just i -> if i >= value then pure m else p
81− Nothing -> pure Nothing
83{-# INLINE takeBetween #-}
123{-# INLINE takeBetween #-}
84−takeBetween :: MonadCatch m => Int -> SerialT m a -> m ()
124+takeBetween :: Monad m => Int -> Stream m a -> m (Either ParseError ())
85−takeBetween value = IP.parse (PR.takeBetween 0 value FL.drain)
125+takeBetween value = Stream.parse (PR.takeBetween 0 value Fold.drain)
87{-# INLINE takeEQ #-}
127{-# INLINE takeEQ #-}
88−takeEQ :: MonadCatch m => Int -> SerialT m a -> m ()
128+takeEQ :: Monad m => Int -> Stream m a -> m (Either ParseError ())
89−takeEQ value = IP.parse (PR.takeEQ value FL.drain)
129+takeEQ value = Stream.parse (PR.takeEQ value Fold.drain)
131+{-# INLINE takeGE #-}
132+takeGE :: Monad m => Int -> Stream m a -> m (Either ParseError ())
133+takeGE value = Stream.parse (PR.takeGE value Fold.drain)
91−{-# INLINE drainWhile #-}
135+{-# INLINE dropWhile #-}
92−drainWhile :: MonadCatch m => Int -> SerialT m Int -> m ()
136+dropWhile :: Monad m => Int -> Stream m Int -> m (Either ParseError ())
93−drainWhile value = IP.parse (PR.drainWhile (<= value))
137+dropWhile value = Stream.parse (PR.dropWhile (<= value))
95−{-# INLINE sliceBeginWith #-}
139+{-# INLINE takeStartBy #-}
96−sliceBeginWith :: MonadCatch m => Int -> SerialT m Int -> m ()
140+takeStartBy :: Monad m => Int -> Stream m Int -> m (Either ParseError ())
97−sliceBeginWith value stream = do
141+takeStartBy value stream = do
98− stream1 <- return . fromMaybe (S.fromPure (value + 1)) =<< S.tail stream
99− let stream2 = value `S.cons` stream1
142+ let stream2 = value `Stream.cons` stream
100− IP.parse (PR.sliceBeginWith (== value) FL.drain) stream2
143+ Stream.parse (PR.takeStartBy (== value) Fold.drain) stream2
145+takeFramedByEsc_ :: Monad m => Int -> Stream m Char -> m (Either ParseError ())
146+takeFramedByEsc_ _ = Stream.parse parser
154+ parser = PR.takeFramedByEsc_ isEsc isBegin isEnd Fold.drain
156+{-# INLINE listEqBy #-}
157+listEqBy :: Int -> Stream IO Int -> IO (Either ParseError [Int])
158+listEqBy len = Stream.parse (PR.listEqBy (==) [1 .. len])
160+{-# INLINE streamEqBy #-}
161+streamEqBy :: Int -> Stream IO Int -> IO (Either ParseError ())
162+streamEqBy len = Stream.parse (PR.streamEqBy (==) (Stream.enumerateFromTo 1 len))
102{-# INLINE takeWhile #-}
164{-# INLINE takeWhile #-}
103−takeWhile :: MonadCatch m => Int -> SerialT m Int -> m ()
165+takeWhile :: Monad m => Int -> Stream m Int -> m (Either ParseError ())
104−takeWhile value = IP.parse (PR.takeWhile (<= value) FL.drain)
166+takeWhile value = Stream.parse (PR.takeWhile (<= value) Fold.drain)
168+takeWhileP :: Monad m => Int -> Stream m Int -> m (Either ParseError ())
170+ Stream.parse (PR.takeWhileP (<= value) (PR.takeWhile (<= value - 1) Fold.drain))
106{-# INLINE takeP #-}
172{-# INLINE takeP #-}
107−takeP :: MonadCatch m => Int -> SerialT m a -> m ()
173+takeP :: Monad m => Int -> Stream m a -> m (Either ParseError ())
108−takeP value = IP.parse (PR.takeP value (PR.fromFold FL.drain))
174+takeP value = Stream.parse (PR.takeP value (PR.fromFold Fold.drain))
110{-# INLINE groupBy #-}
176{-# INLINE groupBy #-}
111−groupBy :: MonadCatch m => SerialT m Int -> m ()
177+groupBy :: Monad m => Stream m Int -> m (Either ParseError ())
112−groupBy = IP.parse (PR.groupBy (<=) FL.drain)
178+groupBy = Stream.parse (PR.groupBy (<=) Fold.drain)
114{-# INLINE groupByRolling #-}
180{-# INLINE groupByRolling #-}
115−groupByRolling :: MonadCatch m => SerialT m Int -> m ()
181+groupByRolling :: Monad m => Stream m Int -> m (Either ParseError ())
116−groupByRolling = IP.parse (PR.groupByRolling (<=) FL.drain)
182+groupByRolling = Stream.parse (PR.groupByRolling (<=) Fold.drain)
118{-# INLINE wordBy #-}
184{-# INLINE wordBy #-}
119−wordBy :: MonadCatch m => Int -> SerialT m Int -> m ()
185+wordBy :: Monad m => Int -> Stream m Int -> m (Either ParseError ())
120−wordBy value = IP.parse (PR.wordBy (>= value) FL.drain)
186+wordBy value = Stream.parse (PR.wordBy (>= value) Fold.drain)
188+{-# INLINE sepByWords #-}
189+sepByWords :: Monad m => Stream m Int -> m (Either ParseError ())
190+sepByWords = Stream.parse (wrds even Fold.drain)
192+ wrds p = PR.sepBy (PR.takeWhile (not . p) Fold.drain) (PR.dropWhile p)
194+{-# INLINE sepByAllWords #-}
195+sepByAllWords :: Monad m => Stream m Int -> m (Either ParseError ())
196+sepByAllWords = Stream.parse (wrds even Fold.drain)
198+ wrds p = PR.sepByAll (PR.takeWhile (not . p) Fold.drain) (PR.dropWhile p)
200+-- Returning a list to compare with the sepBy1 in ParserK
201+{-# INLINE sepBy1 #-}
202+sepBy1 :: Monad m => Stream m Int -> m (Either ParseError [Int])
204+ Stream.parse (PR.sepBy1 (PR.satisfy odd) (PR.satisfy even) Fold.toList) xs
206+{-# INLINE sepByWords1 #-}
207+sepByWords1 :: Monad m => Stream m Int -> m (Either ParseError ())
208+sepByWords1 = Stream.parse (wrds even Fold.drain)
210+ wrds p = PR.sepBy1 (PR.takeWhile (not . p) Fold.drain) (PR.dropWhile p)
212+{-# INLINE deintercalate #-}
213+deintercalate :: Monad m => Int -> Stream m Int -> m (Either ParseError ())
214+deintercalate _ = Stream.parse (partition even)
220+ (PR.takeWhile (not . p) Fold.sum) (PR.takeWhile p Fold.sum) Fold.drain
222+{-# INLINE deintercalate1 #-}
223+deintercalate1 :: Monad m => Int -> Stream m Int -> m (Either ParseError ())
224+deintercalate1 _ = Stream.parse (partition even)
230+ (PR.takeWhile (not . p) Fold.sum) (PR.takeWhile p Fold.sum) Fold.drain
232+{-# INLINE deintercalateAll #-}
233+deintercalateAll :: Monad m => Int -> Stream m Int -> m (Either ParseError ())
234+deintercalateAll _ = Stream.parse (partition even)
240+ (PR.takeWhile (not . p) Fold.sum) (PR.takeWhile p Fold.sum) Fold.drain
122{-# INLINE manyWordByEven #-}
242{-# INLINE manyWordByEven #-}
123−manyWordByEven :: MonadCatch m => SerialT m Int -> m ()
243+manyWordByEven :: Monad m => Stream m Int -> m (Either ParseError ())
124−manyWordByEven = IP.parse (PR.many (PR.wordBy (Prelude.even) FL.drain) FL.drain)
244+manyWordByEven = Stream.parse (PR.many (PR.wordBy even Fold.drain) Fold.drain)
126{-# INLINE many #-}
246{-# INLINE many #-}
127−many :: MonadCatch m => SerialT m Int -> m Int
247+many :: Monad m => Stream m Int -> m (Either ParseError Int)
128−many = IP.parse (PR.many (PR.satisfy (> 0)) FL.length)
248+many = Stream.parse (PR.many (PR.satisfy (> 0)) Fold.length)
130{-# INLINE manyAlt #-}
250{-# INLINE manyAlt #-}
131−manyAlt :: MonadCatch m => SerialT m Int -> m Int
251+manyAlt :: Monad m => Stream m Int -> m Int
132manyAlt xs = do
252manyAlt xs = do
133− x <- IP.parse (AP.many (PR.satisfy (> 0))) xs
253+ x <- Stream.parse (AP.many (PR.satisfy (> 0))) xs
134 return $ Prelude.length x
254 return $ Prelude.length x
136{-# INLINE some #-}
256{-# INLINE some #-}
137−some :: MonadCatch m => SerialT m Int -> m Int
257+some :: Monad m => Stream m Int -> m (Either ParseError Int)
138−some = IP.parse (PR.some (PR.satisfy (> 0)) FL.length)
258+some = Stream.parse (PR.some (PR.satisfy (> 0)) Fold.length)
140{-# INLINE someAlt #-}
260{-# INLINE someAlt #-}
141−someAlt :: MonadCatch m => SerialT m Int -> m Int
261+someAlt :: Monad m => Stream m Int -> m Int
142someAlt xs = do
262someAlt xs = do
143− x <- IP.parse (AP.some (PR.satisfy (> 0))) xs
263+ x <- Stream.parse (AP.some (PR.satisfy (> 0))) xs
144 return $ Prelude.length x
264 return $ Prelude.length x
146{-# INLINE manyTill #-}
266{-# INLINE manyTill #-}
147−manyTill :: MonadCatch m => Int -> SerialT m Int -> m Int
267+manyTill :: Monad m => Int -> Stream m Int -> m (Either ParseError Int)
148manyTill value =
268manyTill value =
149− IP.parse (PR.manyTill (PR.satisfy (> 0)) (PR.satisfy (== value)) FL.length)
269+ Stream.parse (PR.manyTill (PR.satisfy (> 0)) (PR.satisfy (== value)) Fold.length)
151−{-# INLINE splitAp #-}
271+{-# INLINE splitAp2 #-}
152−splitAp :: MonadCatch m
272+splitAp2 :: Monad m
153− => Int -> SerialT m Int -> m ((), ())
273+ => Int -> Stream m Int -> m (Either ParseError ((), ()))
154−splitAp value =
274+splitAp2 value =
155− IP.parse
275+ Stream.parse
157− <$> PR.drainWhile (<= (value `div` 2))
277+ <$> PR.dropWhile (<= (value `div` 2))
158− <*> PR.drainWhile (<= value)
278+ <*> PR.dropWhile (<= value)
281+{-# INLINE splitAp4 #-}
283+ => Int -> Stream m Int -> m (Either ParseError ())
286+ ( (\() () () () -> ())
287+ <$> PR.dropWhile (<= (value * 1 `div` 4))
288+ <*> PR.dropWhile (<= (value * 2 `div` 4))
289+ <*> PR.dropWhile (<= (value * 3 `div` 4))
290+ <*> PR.dropWhile (<= value)
293+{-# INLINE splitAp8 #-}
295+ => Int -> Stream m Int -> m (Either ParseError ())
298+ ( (\() () () () () () () () -> ())
299+ <$> PR.dropWhile (<= (value * 1 `div` 8))
300+ <*> PR.dropWhile (<= (value * 2 `div` 8))
301+ <*> PR.dropWhile (<= (value * 3 `div` 8))
302+ <*> PR.dropWhile (<= (value * 4 `div` 8))
303+ <*> PR.dropWhile (<= (value * 5 `div` 8))
304+ <*> PR.dropWhile (<= (value * 6 `div` 8))
305+ <*> PR.dropWhile (<= (value * 7 `div` 8))
306+ <*> PR.dropWhile (<= value)
161{-# INLINE splitApBefore #-}
309{-# INLINE splitApBefore #-}
162−splitApBefore :: MonadCatch m
310+splitApBefore :: Monad m
163− => Int -> SerialT m Int -> m ()
311+ => Int -> Stream m Int -> m (Either ParseError ())
164splitApBefore value =
312splitApBefore value =
165− IP.parse
313+ Stream.parse
166− ( PR.drainWhile (<= (value `div` 2))
314+ ( PR.dropWhile (<= (value `div` 2))
167− *> PR.drainWhile (<= value)
315+ *> PR.dropWhile (<= value)
170{-# INLINE splitApAfter #-}
318{-# INLINE splitApAfter #-}
171−splitApAfter :: MonadCatch m
319+splitApAfter :: Monad m
172− => Int -> SerialT m Int -> m ()
320+ => Int -> Stream m Int -> m (Either ParseError ())
173splitApAfter value =
321splitApAfter value =
174− IP.parse
322+ Stream.parse
175− ( PR.drainWhile (<= (value `div` 2))
323+ ( PR.dropWhile (<= (value `div` 2))
176− <* PR.drainWhile (<= value)
324+ <* PR.dropWhile (<= value)
179−{-# INLINE serialWith #-}
327+{-# INLINE splitWith2 #-}
180−serialWith :: MonadCatch m
328+splitWith2 :: Monad m
181− => Int -> SerialT m Int -> m ((), ())
329+ => Int -> Stream m Int -> m (Either ParseError ((), ()))
182−serialWith value =
330+splitWith2 value =
183− IP.parse
331+ Stream.parse
184− (PR.serialWith (,)
332+ (PR.splitWith (,)
185− (PR.drainWhile (<= (value `div` 2)))
333+ (PR.dropWhile (<= (value `div` 2)))
186− (PR.drainWhile (<= value))
334+ (PR.dropWhile (<= value))
189{-# INLINE split_ #-}
337{-# INLINE split_ #-}
190−split_ :: MonadCatch m
338+split_ :: Monad m
191− => Int -> SerialT m Int -> m ()
339+ => Int -> Stream m Int -> m (Either ParseError ())
192split_ value =
340split_ value =
193− IP.parse
341+ Stream.parse
194 (PR.split_
342 (PR.split_
195− (PR.drainWhile (<= (value `div` 2)))
343+ (PR.dropWhile (<= (value `div` 2)))
196− (PR.drainWhile (<= value))
344+ (PR.dropWhile (<= value))
199−{-# INLINE sliceSepByP #-}
347+-- XXX dropWhile with applicative does not fuse
200−sliceSepByP :: MonadCatch m
348+-- PR.dropWhile (<= (value * 1 `div` 4)) *> PR.die "alt"
201− => Int -> SerialT m Int -> m()
349+{-# INLINE takeWhileFail #-}
202−sliceSepByP value = IP.parse (PR.sliceSepByP (>= value) (PR.fromFold FL.drain))
350+takeWhileFail :: Monad m => (a -> Bool) -> Fold m a b -> Parser a m b
351+takeWhileFail predicate (Fold fstep finitial _ ffinal) =
352+ Parser step initial extract
358+ return $ case res of
359+ Fold.Partial s -> IPartial s
360+ Fold.Done b -> IDone b
368+ Fold.Partial s1 -> Partial 0 s1
369+ Fold.Done b -> Done 0 b
370+ else return $ Error "fail"
372+ extract s = fmap (Done 0) (ffinal s)
376+ => Int -> Stream m Int -> m (Either ParseError ())
380+ (takeWhileFail (<= (value `div` 2)) Fold.drain)
381+ (PR.dropWhile (<= value))
386+ => Int -> Stream m Int -> m (Either ParseError ())
389+ ( takeWhileFail (<= (value * 1 `div` 4)) Fold.drain
390+ <|> takeWhileFail (<= (value * 2 `div` 4)) Fold.drain
391+ <|> takeWhileFail (<= (value * 3 `div` 4)) Fold.drain
392+ <|> PR.dropWhile (<= value)
397+ => Int -> Stream m Int -> m (Either ParseError ())
400+ ( takeWhileFail (<= (value * 1 `div` 8)) Fold.drain
401+ <|> takeWhileFail (<= (value * 2 `div` 8)) Fold.drain
402+ <|> takeWhileFail (<= (value * 3 `div` 8)) Fold.drain
403+ <|> takeWhileFail (<= (value * 4 `div` 8)) Fold.drain
404+ <|> takeWhileFail (<= (value * 5 `div` 8)) Fold.drain
405+ <|> takeWhileFail (<= (value * 6 `div` 8)) Fold.drain
406+ <|> takeWhileFail (<= (value * 7 `div` 8)) Fold.drain
407+ <|> PR.dropWhile (<= value)
412+ => Int -> Stream m Int -> m (Either ParseError ())
415+ ( takeWhileFail (<= (value * 1 `div` 16)) Fold.drain
416+ <|> takeWhileFail (<= (value * 2 `div` 16)) Fold.drain
417+ <|> takeWhileFail (<= (value * 3 `div` 16)) Fold.drain
418+ <|> takeWhileFail (<= (value * 4 `div` 16)) Fold.drain
419+ <|> takeWhileFail (<= (value * 5 `div` 16)) Fold.drain
420+ <|> takeWhileFail (<= (value * 6 `div` 16)) Fold.drain
421+ <|> takeWhileFail (<= (value * 8 `div` 16)) Fold.drain
422+ <|> takeWhileFail (<= (value * 9 `div` 16)) Fold.drain
423+ <|> takeWhileFail (<= (value * 10 `div` 16)) Fold.drain
424+ <|> takeWhileFail (<= (value * 11 `div` 16)) Fold.drain
425+ <|> takeWhileFail (<= (value * 12 `div` 16)) Fold.drain
426+ <|> takeWhileFail (<= (value * 13 `div` 16)) Fold.drain
427+ <|> takeWhileFail (<= (value * 14 `div` 16)) Fold.drain
428+ <|> takeWhileFail (<= (value * 15 `div` 16)) Fold.drain
429+ <|> PR.dropWhile (<= value)
432+{-# INLINE altSmall #-}
434+ => Int -> Stream m Int -> m ()
436+ Stream.fold Fold.drain .
439+ (PR.satisfy (>= value) *> PR.die "alt")
440+ (PR.satisfy (<= value))
445+ => Int -> Stream m Int -> m (Either ParseError ())
449+ PR.dropWhile (<= (value `div` 2))
450+ PR.dropWhile (<= value)
452+{-# INLINE monad4 #-}
454+ => Int -> Stream m Int -> m (Either ParseError ())
457+ PR.dropWhile (<= (value `div` 4))
458+ PR.dropWhile (<= (value `div` 2))
459+ PR.dropWhile (<= (value * 3 `div` 4))
460+ PR.dropWhile (<= value)
462+{-# INLINE monad8 #-}
464+ => Int -> Stream m Int -> m (Either ParseError ())
467+ PR.dropWhile (<= (value * 1 `div` 8))
468+ PR.dropWhile (<= (value * 2 `div` 8))
469+ PR.dropWhile (<= (value * 3 `div` 8))
470+ PR.dropWhile (<= (value * 4 `div` 8))
471+ PR.dropWhile (<= (value * 5 `div` 8))
472+ PR.dropWhile (<= (value * 6 `div` 8))
473+ PR.dropWhile (<= (value * 7 `div` 8))
474+ PR.dropWhile (<= value)
476+{-# INLINE monad16 #-}
478+ => Int -> Stream m Int -> m (Either ParseError ())
481+ PR.dropWhile (<= (value * 1 `div` 16))
482+ PR.dropWhile (<= (value * 2 `div` 16))
483+ PR.dropWhile (<= (value * 3 `div` 16))
484+ PR.dropWhile (<= (value * 4 `div` 16))
485+ PR.dropWhile (<= (value * 5 `div` 16))
486+ PR.dropWhile (<= (value * 6 `div` 16))
487+ PR.dropWhile (<= (value * 7 `div` 16))
488+ PR.dropWhile (<= (value * 8 `div` 16))
489+ PR.dropWhile (<= (value * 9 `div` 16))
490+ PR.dropWhile (<= (value * 10 `div` 16))
491+ PR.dropWhile (<= (value * 11 `div` 16))
492+ PR.dropWhile (<= (value * 12 `div` 16))
493+ PR.dropWhile (<= (value * 13 `div` 16))
494+ PR.dropWhile (<= (value * 14 `div` 16))
495+ PR.dropWhile (<= (value * 15 `div` 16))
496+ PR.dropWhile (<= value)
498+{-# INLINE takeEndBy_ #-}
499+takeEndBy_ :: Monad m
500+ => Int -> Stream m Int -> m (Either ParseError ())
501+takeEndBy_ value = Stream.parse (PR.takeEndBy_ (>= value) (PR.fromFold Fold.drain))
204{-# INLINE teeAllAny #-}
504{-# INLINE teeAllAny #-}
205−teeAllAny :: MonadCatch m
505+teeAllAny :: Monad m
206− => Int -> SerialT m Int -> m ((), ())
506+ => Int -> Stream m Int -> m ((), ())
207teeAllAny value =
507teeAllAny value =
208− IP.parse
508+ Stream.parse
209 (PR.teeWith (,)
509 (PR.teeWith (,)
210− (PR.drainWhile (<= value))
510+ (PR.dropWhile (<= value))
211− (PR.drainWhile (<= value))
511+ (PR.dropWhile (<= value))
214{-# INLINE teeFstAllAny #-}
514{-# INLINE teeFstAllAny #-}
215−teeFstAllAny :: MonadCatch m
515+teeFstAllAny :: Monad m
216− => Int -> SerialT m Int -> m ((), ())
516+ => Int -> Stream m Int -> m ((), ())
217teeFstAllAny value =
517teeFstAllAny value =
218− IP.parse
518+ Stream.parse
219 (PR.teeWithFst (,)
519 (PR.teeWithFst (,)
220− (PR.drainWhile (<= value))
520+ (PR.dropWhile (<= value))
221− (PR.drainWhile (<= value))
521+ (PR.dropWhile (<= value))
224{-# INLINE shortestAllAny #-}
524{-# INLINE shortestAllAny #-}
225−shortestAllAny :: MonadCatch m
525+shortestAllAny :: Monad m
226− => Int -> SerialT m Int -> m ()
526+ => Int -> Stream m Int -> m (Either ParseError ())
227shortestAllAny value =
527shortestAllAny value =
228− IP.parse
528+ Stream.parse
229 (PR.shortest
529 (PR.shortest
230− (PR.drainWhile (<= value))
530+ (PR.dropWhile (<= value))
231− (PR.drainWhile (<= value))
531+ (PR.dropWhile (<= value))
234{-# INLINE longestAllAny #-}
534{-# INLINE longestAllAny #-}
235−longestAllAny :: MonadCatch m
535+longestAllAny :: Monad m
236− => Int -> SerialT m Int -> m ()
536+ => Int -> Stream m Int -> m (Either ParseError ())
237longestAllAny value =
537longestAllAny value =
238− IP.parse
538+ Stream.parse
239 (PR.longest
539 (PR.longest
240− (PR.drainWhile (<= value))
540+ (PR.dropWhile (<= value))
241− (PR.drainWhile (<= value))
541+ (PR.dropWhile (<= value))
244−parseManyChunksOfSum :: Int -> Handle -> IO Int
245−parseManyChunksOfSum n inh =
248− (PR.fromFold $ FL.take n FL.sum)
249− (S.unfold Handle.read inh)
251-------------------------------------------------------------------------------
545-------------------------------------------------------------------------------
252−-- Parsing with unfolds
546+-- Spanning
253-------------------------------------------------------------------------------
547-------------------------------------------------------------------------------
255−{-# INLINE parseManyUnfoldArrays #-}
549+{-# INLINE span #-}
256−parseManyUnfoldArrays :: Int -> [Array.Array Int] -> IO ()
550+span :: Monad m => Int -> Stream m Int -> m (Either ParseError ((), ()))
257−parseManyUnfoldArrays count arrays = do
551+span value = Stream.parse (PR.span (<= (value `div` 2)) Fold.drain Fold.drain)
258− let src = Source.source (Just (Producer.OuterLoop arrays))
552+
553+{-# INLINE spanBy #-}
554+spanBy :: Monad m => Int -> Stream m Int -> m (Either ParseError ((), ()))
556+ Stream.parse (PR.spanBy (\_ i -> i <= (value `div` 2)) Fold.drain Fold.drain)
558+{-# INLINE spanByRolling #-}
559+spanByRolling :: Monad m => Int -> Stream m Int -> m (Either ParseError ((), ()))
560+spanByRolling value =
561+ Stream.parse (PR.spanByRolling (\_ i -> i <= value `div` 2) Fold.drain Fold.drain)
563+parseManyChunksOfSum :: Int -> Handle -> IO Int
564+parseManyChunksOfSum n inh =
565+ Stream.fold Fold.length
259− let parser = PR.fromFold (FL.take count FL.drain)
567+ (PR.fromFold $ Fold.take n Fold.sum)
260− let readSrc =
568+ (Stream.unfold Handle.reader inh)
262− $ Producer.concat Producer.fromList Array.producer
264− Producer.simplify (Source.parseMany parser readSrc)
265− S.drain $ S.unfold streamParser src
267-------------------------------------------------------------------------------
570-------------------------------------------------------------------------------
268-- Parsers in which -fspec-constr-recursive=16 is problematic
571-- Parsers in which -fspec-constr-recursive=16 is problematic
@@ -273,63 +576,129 @@ parseManyUnfoldArrays count arrays = do
273-- not have to rely on it.
576-- not have to rely on it.
275{-# INLINE lookAhead #-}
578{-# INLINE lookAhead #-}
276−lookAhead :: MonadCatch m => Int -> SerialT m Int -> m ()
579+lookAhead :: Monad m => Int -> Stream m Int -> m (Either ParseError ())
277lookAhead value =
580lookAhead value =
278− IP.parse (PR.lookAhead (PR.takeWhile (<= value) FL.drain) $> ())
581+ Stream.parse (PR.lookAhead (PR.takeWhile (<= value) Fold.drain) $> ())
583+-- XXX The timing of this increased 3x after the stepify extract changes.
584+{-# INLINE sequenceA_ #-}
585+sequenceA_ :: Monad m => Int -> Stream m Int -> m (Either ParseError ())
587+ Stream.parse (F.sequenceA_ $ replicate value (PR.satisfy (> 0)))
589+-- quadratic complexity
280{-# INLINE sequenceA #-}
590{-# INLINE sequenceA #-}
281−sequenceA :: MonadCatch m => Int -> SerialT m Int -> m Int
591+sequenceA :: Monad m => Int -> Stream m Int -> m Int
282sequenceA value xs = do
592sequenceA value xs = do
283− x <- IP.parse (TR.sequenceA (replicate value (PR.satisfy (> 0)))) xs
593+ x <- Stream.parse (TR.sequenceA (replicate value (PR.satisfy (> 0)))) xs
284 return $ length x
594 return $ length x
286−{-# INLINE sequenceA_ #-}
596+-- quadratic complexity
287−sequenceA_ :: MonadCatch m => Int -> SerialT m Int -> m ()
289− IP.parse (F.sequenceA_ $ replicate value (PR.satisfy (> 0)))
291{-# INLINE sequence #-}
597{-# INLINE sequence #-}
292−sequence :: MonadCatch m => Int -> SerialT m Int -> m Int
598+sequence :: Monad m => Int -> Stream m Int -> m Int
293sequence value xs = do
599sequence value xs = do
294− x <- IP.parse (TR.sequence (replicate value (PR.satisfy (> 0)))) xs
600+ x <- Stream.parse (TR.sequence (replicate value (PR.satisfy (> 0)))) xs
295 return $ length x
601 return $ length x
297{-# INLINE sequence_ #-}
603{-# INLINE sequence_ #-}
298−sequence_ :: MonadCatch m => Int -> SerialT m Int -> m ()
604+sequence_ :: Monad m => Int -> Stream m Int -> m (Either ParseError ())
299−sequence_ value =
605+sequence_ value xs =
300− IP.parse (F.sequence_ $ replicate value (PR.satisfy (> 0)))
606+ Stream.parse (foldr f (return ()) (replicate value (PR.takeBetween 0 1 Fold.drain))) xs
611+ f m k = m >>= (\_ -> k)
613+-- choice using the "Alternative" instance with direct style parser type has
614+-- quadratic performance complexity.
302{-# INLINE choiceAsum #-}
616{-# INLINE choiceAsum #-}
303−choiceAsum :: MonadCatch m => Int -> SerialT m Int -> m Int
617+choiceAsum :: Monad m => Int -> Stream m Int -> m (Either ParseError Int)
304choiceAsum value =
618choiceAsum value =
305− IP.parse (asum (replicate value (PR.satisfy (< 0)))
619+ Stream.parse (F.asum (replicate value (PR.satisfy (< 0)))
306 AP.<|> PR.satisfy (> 0))
620 AP.<|> PR.satisfy (> 0))
308{-# INLINE choice #-}
623{-# INLINE choice #-}
309−choice :: MonadCatch m => Int -> SerialT m Int -> m Int
624+choice :: Monad m => Int -> Stream m Int -> m (Either ParseError Int)
310choice value =
625choice value =
311− IP.parse
626+ Stream.parse
312 (PR.choice (replicate value (PR.satisfy (< 0))) AP.<|> PR.satisfy (> 0))
627 (PR.choice (replicate value (PR.satisfy (< 0))) AP.<|> PR.satisfy (> 0))
630+-------------------------------------------------------------------------------
631+-- Parsing with unfolds
632+-------------------------------------------------------------------------------
634+{-# INLINE parseManyUnfoldArrays #-}
635+parseManyUnfoldArrays :: Int -> [Array.Array Int] -> IO ()
636+parseManyUnfoldArrays count arrays = do
637+ let src = Producer.source (Just (Producer.OuterLoop arrays))
638+ let parser = PR.fromFold (Fold.take count Fold.drain)
641+ $ Producer.concat Producer.fromList Array.producer
643+ Producer.simplify (Producer.parseMany parser readSrc)
644+ Stream.fold Fold.drain $ Stream.unfold streamParser src
314-------------------------------------------------------------------------------
646-------------------------------------------------------------------------------
315-- Stream transformation
647-- Stream transformation
316-------------------------------------------------------------------------------
648-------------------------------------------------------------------------------
318{-# INLINE parseMany #-}
650{-# INLINE parseMany #-}
319−parseMany :: MonadCatch m => Int -> SerialT m Int -> m ()
651+parseMany :: Monad m => Int -> Stream m Int -> m ()
320parseMany n =
652parseMany n =
321− S.drain
653+ Stream.fold Fold.drain
322− . S.map getSum
654+ . fmap getSum
323− . IP.parseMany (PR.fromFold $ FL.take n FL.mconcat)
655+ . Stream.catRights . Stream.parseMany (PR.fromFold $ Fold.take n Fold.mconcat)
324− . S.map Sum
656+ . fmap Sum
658+{-# INLINE parseManyGroupBy #-}
659+parseManyGroupBy :: Monad m => (Int -> Int -> Bool) -> Stream m Int -> m ()
660+parseManyGroupBy cmp =
661+ Stream.fold Fold.drain . Stream.parseMany (PR.groupBy cmp Fold.drain)
663+{-# INLINE parseManyGroupsRolling #-}
664+parseManyGroupsRolling :: Monad m => Bool -> Stream m Int -> m ()
665+parseManyGroupsRolling b =
666+ Stream.fold Fold.drain
667+ . Stream.parseMany (PR.groupByRolling (\_ _ -> b) Fold.drain)
669+{-# INLINE parseManyGroupsRollingEither #-}
670+parseManyGroupsRollingEither :: Monad m =>
671+ (Int -> Int -> Bool) -> Int -> m ()
672+parseManyGroupsRollingEither cmp value = do
673+ sourceUnfoldrM value 1
674+ & Stream.parseMany (PR.groupByRollingEither cmp Fold.drain Fold.drain)
675+ & Stream.fold Fold.drain
677+{-# INLINE parseManyGroupsRollingEitherAlt #-}
678+parseManyGroupsRollingEitherAlt :: Monad m =>
679+ (Int -> Int -> Bool) -> Int -> m ()
680+parseManyGroupsRollingEitherAlt cmp value = do
681+ sourceUnfoldrM value 1
682+ -- Make the input unsorted.
683+ & fmap (\x -> if even x then x + 2 else x)
684+ & Stream.parseMany (PR.groupByRollingEither cmp Fold.drain Fold.drain)
685+ & Stream.fold Fold.drain
326{-# INLINE parseIterate #-}
687{-# INLINE parseIterate #-}
327−parseIterate :: MonadCatch m => Int -> SerialT m Int -> m ()
688+parseIterate :: Monad m => Int -> Stream m Int -> m ()
328parseIterate n =
689parseIterate n =
329− S.drain
690+ Stream.fold Fold.drain
330− . S.map getSum
691+ . fmap getSum
693+ . Stream.parseIterate
331− . IP.parseIterate (PR.fromFold . FL.take n . FL.sconcat) (Sum 0)
694+ (PR.fromFold . Fold.take n . Fold.sconcat)
332− . S.map Sum
696+ . fmap Sum
698+{-# INLINE concatSequence #-}
699+concatSequence :: Monad m => Stream m Int -> m (Either ParseError ())
701+ Stream.parse $ PR.sequence (Stream.repeat PR.one) Fold.drain
334-------------------------------------------------------------------------------
703-------------------------------------------------------------------------------
335-- Benchmarks
704-- Benchmarks
@@ -338,42 +707,95 @@ parseIterate n =
338moduleName :: String
707moduleName :: String
339moduleName = "Data.Parser"
708moduleName = "Data.Parser"
710+instance NFData ParseError where
712+ rnf (ParseError x) = rnf x
341o_1_space_serial :: Int -> [Benchmark]
714o_1_space_serial :: Int -> [Benchmark]
342o_1_space_serial value =
715o_1_space_serial value =
343− [ benchIOSink value "next" $ next value
344− , benchIOSink value "takeBetween" $ takeBetween value
716+ [ benchIOSink value "takeBetween" $ takeBetween value
345− , benchIOSink value "takeEQ" $ takeEQ value
346 , benchIOSink value "takeWhile" $ takeWhile value
717 , benchIOSink value "takeWhile" $ takeWhile value
718+ , benchIOSink value "takeWhileP" $ takeWhileP value
347 , benchIOSink value "takeP" $ takeP value
719 , benchIOSink value "takeP" $ takeP value
348− , benchIOSink value "drainWhile" $ drainWhile value
720+ , benchIOSink value "dropWhile" $ dropWhile value
349− , benchIOSink value "sliceBeginWith" $ sliceBeginWith value
721+ , benchIOSink value "takeStartBy" $ takeStartBy value
722+ , benchIOSink value "takeEndBy_" $ takeEndBy_ value
350 , benchIOSink value "groupBy" $ groupBy
723 , benchIOSink value "groupBy" $ groupBy
351 , benchIOSink value "groupByRolling" $ groupByRolling
724 , benchIOSink value "groupByRolling" $ groupByRolling
352 , benchIOSink value "wordBy" $ wordBy value
725 , benchIOSink value "wordBy" $ wordBy value
353− , benchIOSink value "splitAp" $ splitAp value
726+ , benchIOSink value "sepBy (words)" sepByWords
727+ , benchIOSink value "sepByAll (words)" sepByAllWords
728+ , benchIOSink value "sepBy1 (words)" sepByWords1
729+ , benchIOSink value "deintercalate" $ deintercalate value
730+ , benchIOSink value "deintercalate1" $ deintercalate1 value
731+ , benchIOSink value "deintercalateAll" $ deintercalateAll value
732+ -- Applicative and Monad
733+ , benchIOSink value "splitAp2" $ splitAp2 value
734+ , benchIOSink value "splitAp4" $ splitAp4 value
735+ , benchIOSink value "splitAp8" $ splitAp8 value
354 , benchIOSink value "splitApBefore" $ splitApBefore value
736 , benchIOSink value "splitApBefore" $ splitApBefore value
355 , benchIOSink value "splitApAfter" $ splitApAfter value
737 , benchIOSink value "splitApAfter" $ splitApAfter value
356− , benchIOSink value "serialWith" $ serialWith value
738+ , benchIOSink value "splitWith2" $ splitWith2 value
739+ , benchIOSink value "span" $ span value
740+ , benchIOSink value "spanBy" $ spanBy value
741+ , benchIOSink value "spanByRolling" $ spanByRolling value
742+ , benchIOSink value "monad2" $ monad value
357− , benchIOSink value "sliceSepByP" $ sliceSepByP value
743+ , benchIOSink value "monad4" $ monad4 value
744+ , benchIOSink value "monad8" $ monad8 value
746+ , benchIOSink value "alt2parseMany" $ altSmall value
747+ , benchIOSink value "alt2" $ alt2 value
748+ , benchIOSink value "alt4" $ alt4 value
749+ , benchIOSink value "alt8" $ alt8 value
750+ , benchIOSink value "alt16" $ alt16 value
358 , benchIOSink value "many" many
751 , benchIOSink value "many" many
359 , benchIOSink value "many (wordBy even)" $ manyWordByEven
752 , benchIOSink value "many (wordBy even)" $ manyWordByEven
360 , benchIOSink value "some" some
753 , benchIOSink value "some" some
361 , benchIOSink value "manyTill" $ manyTill value
754 , benchIOSink value "manyTill" $ manyTill value
362− , benchIOSink value "tee" $ teeAllAny value
755+ , benchIOSink value "parseMany" $ parseMany value
363− , benchIOSink value "teeFst" $ teeFstAllAny value
364− , benchIOSink value "shortest" $ shortestAllAny value
365− , benchIOSink value "longest" $ longestAllAny value
366 , benchIOSink value "parseMany (take 1)" (parseMany 1)
756 , benchIOSink value "parseMany (take 1)" (parseMany 1)
367 , benchIOSink value "parseMany (take all)" (parseMany value)
757 , benchIOSink value "parseMany (take all)" (parseMany value)
758+ , benchIOSink value "parseMany (groupBy (<))" (parseManyGroupBy (<))
759+ , benchIOSink value "parseMany (groupBy (==))" (parseManyGroupBy (==))
760+ , benchIOSink value "parseMany groupRollingBy (bound groups)"
761+ $ parseManyGroupsRolling False
762+ , benchIOSink value "parseMany groupRollingBy (1 group)"
763+ $ parseManyGroupsRolling True
764+ , bench "parseMany groupRollingByEither (Left)"
765+ $ nfIO $ parseManyGroupsRollingEitherLeft
766+ , bench "parseMany groupRollingByEither (Right)"
767+ $ nfIO $ parseManyGroupsRollingEitherRight
768+ , bench "parseMany groupRollingByEither (Alternating)"
769+ $ nfIO $ parseManyGroupsRollingEitherAlt1
368 , benchIOSink value "parseIterate (take 1)" (parseIterate 1)
770 , benchIOSink value "parseIterate (take 1)" (parseIterate 1)
369 , benchIOSink value "parseIterate (take all)" (parseIterate value)
771 , benchIOSink value "parseIterate (take all)" (parseIterate value)
772+ , benchIOSink value "concatSequence" concatSequence
774+ , benchIOSink value "tee" $ teeAllAny value
775+ , benchIOSink value "teeFst" $ teeFstAllAny value
776+ , benchIOSink value "shortest" $ shortestAllAny value
777+ , benchIOSink value "longest" $ longestAllAny value
779+ , benchIOSink value "streamEqBy" (streamEqBy value)
784+ {-# NOINLINE parseManyGroupsRollingEitherLeft #-}
785+ parseManyGroupsRollingEitherLeft = parseManyGroupsRollingEither (<) value
787+ {-# NOINLINE parseManyGroupsRollingEitherRight #-}
788+ parseManyGroupsRollingEitherRight = parseManyGroupsRollingEither (>) value
790+ {-# NOINLINE parseManyGroupsRollingEitherAlt1 #-}
791+ parseManyGroupsRollingEitherAlt1 =
792+ parseManyGroupsRollingEitherAlt (>) value
372o_1_space_filesystem :: BenchEnv -> [Benchmark]
794o_1_space_filesystem :: BenchEnv -> [Benchmark]
373o_1_space_filesystem env =
795o_1_space_filesystem env =
374− [ mkBench ("S.parseMany (FL.take " ++ show (bigSize env) ++ " FL.sum)") env
796+ [ mkBench ("S.parseMany (Fold.take " ++ show (bigSize env) ++ " Fold.sum)") env
375 $ \inh _ -> noinline parseManyChunksOfSum (bigSize env) inh
797 $ \inh _ -> noinline parseManyChunksOfSum (bigSize env) inh
376− , mkBench "S.parseMany (FL.take 1 FL.sum)" env
798+ , mkBench "S.parseMany (Fold.take 1 Fold.sum)" env
377 $ \inh _ -> inline parseManyChunksOfSum 1 inh
799 $ \inh _ -> inline parseManyChunksOfSum 1 inh
@@ -388,26 +810,38 @@ o_1_space_serial_unfold bound arrays =
388o_n_heap_serial :: Int -> [Benchmark]
810o_n_heap_serial :: Int -> [Benchmark]
389o_n_heap_serial value =
811o_n_heap_serial value =
813+ benchIOSink value "takeEQ" $ takeEQ value
814+ , benchIOSink value "takeGE" $ takeGE value
391 -- lookahead benchmark holds the entire input till end
816 -- lookahead benchmark holds the entire input till end
392− benchIOSink value "lookAhead" $ lookAhead value
817+ , benchIOSink value "lookAhead" $ lookAhead value
394− -- accumulates the results in a list
819+ -- o-n-heap because of backtracking
395− , benchIOSink value "sequence" $ sequence value
820+ , benchIOSrc sourceEscapedFrames value "takeFramedByEsc_"
396− , benchIOSink value "sequenceA" $ sequenceA value
821+ $ takeFramedByEsc_ value
398− -- XXX why should this take O(n) heap, it discards the results?
399− , benchIOSink value "sequence_" $ sequence_ value
400− , benchIOSink value "sequenceA_" $ sequenceA_ value
401 -- non-linear time complexity (parserD)
823 -- non-linear time complexity (parserD)
402 , benchIOSink value "split_" $ split_ value
824 , benchIOSink value "split_" $ split_ value
403− -- XXX why O(n) heap?
825+ -- XXX Takes lot of space when run on a long stream, why?
404− , benchIOSink value "choice (asum)" $ choiceAsum value
826+ , benchIOSink value "monad16" $ monad16 value
405− , benchIOSink value "choice" $ choice value
407 -- These show non-linear time complexity.
828 -- These show non-linear time complexity.
408 -- They accumulate the results in a list.
829 -- They accumulate the results in a list.
830+ , benchIOSink value "sepBy1" sepBy1
409 , benchIOSink value "manyAlt" manyAlt
831 , benchIOSink value "manyAlt" manyAlt
410 , benchIOSink value "someAlt" someAlt
832 , benchIOSink value "someAlt" someAlt
833+ , benchIOSink value "listEqBy" (listEqBy value)
836+-- accumulate results in a list in IO
837+o_n_space_serial :: Int -> [Benchmark]
838+o_n_space_serial value =
839+ [ benchIOSink value "sequenceA/100" $ sequenceA (value `div` 100)
840+ , benchIOSink value "sequenceA_/100" $ sequenceA_ (value `div` 100)
841+ , benchIOSink value "sequence/100" $ sequence (value `div` 100)
842+ , benchIOSink value "sequence_/100" $ sequence_ (value `div` 100)
843+ , benchIOSink value "choice (asum)/100" $ choiceAsum (value `div` 100)
844+ -- , benchIOSink value "choice/100" $ choice (value `div` 100)
413-------------------------------------------------------------------------------
847-------------------------------------------------------------------------------
@@ -416,12 +850,13 @@ o_n_heap_serial value =
417main :: IO ()
851main :: IO ()
419 env <- mkHandleBenchEnv
854 env <- mkHandleBenchEnv
420 runWithCLIOptsEnv defaultStreamSize alloc (allBenchmarks env)
855 runWithCLIOptsEnv defaultStreamSize alloc (allBenchmarks env)
424− alloc value = IP.toList $ IP.arraysOf 100 $ sourceUnfoldrM value 0
859+ alloc value = Stream.fold Fold.toList $ Stream.chunksOf 100 $ sourceUnfoldrM value 0
426 allBenchmarks env arrays value =
861 allBenchmarks env arrays value =
427 [ bgroup (o_1_space_prefix moduleName) (o_1_space_serial value)
862 [ bgroup (o_1_space_prefix moduleName) (o_1_space_serial value)
@@ -431,4 +866,22 @@ main = do
431 , bgroup (o_1_space_prefix moduleName)
866 , bgroup (o_1_space_prefix moduleName)
432 (o_1_space_serial_unfold value arrays)
867 (o_1_space_serial_unfold value arrays)
433 , bgroup (o_n_heap_prefix moduleName) (o_n_heap_serial value)
868 , bgroup (o_n_heap_prefix moduleName) (o_n_heap_serial value)
869+ , bgroup (o_n_space_prefix moduleName) (o_n_space_serial value)
872+ -- Enable FUSION_CHECK macro at the beginning of the file
873+ -- Enable one benchmark below, and run the benchmark
874+ -- Check the .dump-simpl output
876+ -- let input = sourceUnfoldrM value 1
877+ -- manyTill value input
878+ -- deintercalate value input
879+ -- deintercalate1 value input
880+ -- deintercalateAll value input
882+ -- sepByAllWords input
884+ -- sepByWords1 input
885+ takeFramedByEsc_ value (sourceEscapedFrames value 1)