2-- Module : Streamly.Internal.Benchmark.FileIO.Array
3-- Copyright : (c) 2019 Composewell Technologies
6-- Maintainer : streamly@composewell.com
7-- Stability : experimental
12#ifdef __HADDOCK_VERSION__
17{-# LANGUAGE TemplateHaskell #-}
18{-# OPTIONS_GHC -fplugin Test.Inspection.Plugin #-}
21module Streamly.Internal.Benchmark.FileIO.Array
36 , copyCodecUtf8Lenient
40import Data.Functor.Identity (runIdentity)
41import Data.Word (Word8)
42import System.IO (Handle, hClose)
43import Prelude hiding (last)
45import qualified Streamly.FileSystem.Handle as FH
46import qualified Streamly.Memory.Array as A
47import qualified Streamly.Prelude as S
48import qualified Streamly.Data.Unicode.Stream as SS
49import qualified Streamly.Internal.Data.Unicode.Stream as IUS
51import qualified Streamly.Internal.FileSystem.Handle as IFH
52import qualified Streamly.Internal.Memory.Array as IA
53import qualified Streamly.Internal.Memory.ArrayStream as AS
54import qualified Streamly.Internal.Data.Unfold as IUF
57import Foreign.Storable (Storable)
58import Streamly.Internal.Data.Stream.StreamD.Type (Step(..))
62-- | Get the last byte from a file bytestream.
64last :: Handle -> IO (Maybe Word8)
66 let s = IFH.toChunks inh
70 Just arr -> IA.readIndex arr (A.length arr - 1)
73inspect $ hasNoTypeClasses 'last
74inspect $ 'last `hasNoType` ''Step
77-- | Count the number of bytes in a file.
78{-# INLINE countBytes #-}
79countBytes :: Handle -> IO Int
81 let s = IFH.toChunks inh
82 in S.sum (S.map A.length s)
85inspect $ hasNoTypeClasses 'countBytes
86inspect $ 'countBytes `hasNoType` ''Step
89-- | Count the number of lines in a file.
90{-# INLINE countLines #-}
91countLines :: Handle -> IO Int
92countLines = S.length . AS.splitOnSuffix 10 . IFH.toChunks
95inspect $ hasNoTypeClasses 'countLines
96inspect $ 'countLines `hasNoType` ''Step
99-- XXX use a word splitting combinator instead of splitOn and test it.
100-- | Count the number of lines in a file.
101{-# INLINE countWords #-}
102countWords :: Handle -> IO Int
103countWords = S.length . AS.splitOn 32 . IFH.toChunks
106inspect $ hasNoTypeClasses 'countWords
107inspect $ 'countWords `hasNoType` ''Step
110-- | Sum the bytes in a file.
111{-# INLINE sumBytes #-}
112sumBytes :: Handle -> IO Word8
114 let foldlArr' f z = runIdentity . S.foldl' f z . IA.toStream
115 let s = IFH.toChunks inh
116 S.foldl' (\acc arr -> acc + foldlArr' (+) 0 arr) 0 s
119inspect $ hasNoTypeClasses 'sumBytes
120inspect $ 'sumBytes `hasNoType` ''Step
123-- | Send the file contents to /dev/null
125cat :: Handle -> Handle -> IO ()
127 S.fold (IFH.writeChunks devNull) $ IFH.toChunksWithBufferOf (256*1024) inh
130inspect $ hasNoTypeClasses 'cat
131inspect $ 'cat `hasNoType` ''Step
134-- | Send the file contents to /dev/null with exception handling
135{-# INLINE catBracket #-}
136catBracket :: Handle -> Handle -> IO ()
137catBracket devNull inh =
138 let readEx = IUF.bracket return (\_ -> hClose inh)
139 (IUF.supplyFirst FH.readChunksWithBufferOf (256*1024))
140 in IUF.fold readEx (IFH.writeChunks devNull) inh
143inspect $ hasNoTypeClasses 'catBracket
144-- inspect $ 'catBracket `hasNoType` ''Step
147-- | Send the file contents to /dev/null with exception handling
148{-# INLINE catBracketStream #-}
149catBracketStream :: Handle -> Handle -> IO ()
150catBracketStream devNull inh =
151 let readEx = S.bracket (return ()) (\_ -> hClose inh)
152 (\_ -> IFH.toChunksWithBufferOf (256*1024) inh)
153 in S.fold (IFH.writeChunks devNull) $ readEx
156inspect $ hasNoTypeClasses 'catBracketStream
157-- inspect $ 'catBracketStream `hasNoType` ''Step
160-- | Send the file contents to /dev/null with exception handling
161{-# INLINE catOnException #-}
162catOnException :: Handle -> Handle -> IO ()
163catOnException devNull inh =
164 let readEx = IUF.onException (\_ -> hClose inh)
165 (IUF.supplyFirst FH.readChunksWithBufferOf (256*1024))
166 in IUF.fold readEx (IFH.writeChunks devNull) inh
169inspect $ hasNoTypeClasses 'catOnException
170-- inspect $ 'catOnException `hasNoType` ''Step
175copy :: Handle -> Handle -> IO ()
177 let s = IFH.toChunks inh
178 in S.fold (IFH.writeChunks outh) s
181inspect $ hasNoTypeClasses 'copy
182inspect $ 'copy `hasNoType` ''Step
185-- | Lines and unlines
186{-# INLINE linesUnlinesCopy #-}
187linesUnlinesCopy :: Handle -> Handle -> IO ()
188linesUnlinesCopy inh outh =
189 S.fold (IFH.writeWithBufferOf (1024*1024) outh)
190 $ AS.interposeSuffix 10
191 $ AS.splitOnSuffix 10
192 $ IFH.toChunksWithBufferOf (1024*1024) inh
195inspect $ hasNoTypeClassesExcept 'linesUnlinesCopy [''Storable]
196-- inspect $ 'linesUnlinesCopy `hasNoType` ''Step
199-- | Words and unwords
200{-# INLINE wordsUnwordsCopy #-}
201wordsUnwordsCopy :: Handle -> Handle -> IO ()
202wordsUnwordsCopy inh outh =
203 S.fold (IFH.writeWithBufferOf (1024*1024) outh)
205 -- XXX this is not correct word splitting combinator
207 $ IFH.toChunksWithBufferOf (1024*1024) inh
210inspect $ hasNoTypeClassesExcept 'wordsUnwordsCopy [''Storable]
211-- inspect $ 'wordsUnwordsCopy `hasNoType` ''Step
214{-# INLINE decodeUtf8Lenient #-}
215decodeUtf8Lenient :: Handle -> IO ()
216decodeUtf8Lenient inh =
218 $ IUS.decodeUtf8ArraysLenient
219 $ IFH.toChunksWithBufferOf (1024*1024) inh
222inspect $ hasNoTypeClasses 'decodeUtf8Lenient
223-- inspect $ 'decodeUtf8Lenient `hasNoType` ''Step
224-- inspect $ 'decodeUtf8Lenient `hasNoType` ''AT.FlattenState
225-- inspect $ 'decodeUtf8Lenient `hasNoType` ''D.ConcatMapUState
229{-# INLINE copyCodecUtf8Lenient #-}
230copyCodecUtf8Lenient :: Handle -> Handle -> IO ()
231copyCodecUtf8Lenient inh outh =
232 S.fold (FH.write outh)
234 $ IUS.decodeUtf8ArraysLenient
235 $ IFH.toChunksWithBufferOf (1024*1024) inh
238inspect $ hasNoTypeClasses 'copyCodecUtf8Lenient
239-- inspect $ 'copyCodecUtf8Lenient `hasNoType` ''Step
240-- inspect $ 'copyCodecUtf8Lenient `hasNoType` ''AT.FlattenState
241-- inspect $ 'copyCodecUtf8Lenient `hasNoType` ''D.ConcatMapUState
keysesc to close
- j k
- move down, up
- enter
- open
- esc
- back, or up a level
- 1 2 3 4
- readme, files, commits, refs
- /
- filter
- y
- copy the clone command
- c
- compare the chosen commit with another (or shift-click both)
- ?
- show or hide this list