on fe28607 help sign in
106 lines 3.5 kB history raw
1#include "inline.hs"
3-- |
4-- Module : Streamly.Data.Array.Foreign
5-- Copyright : (c) 2019 Composewell Technologies
6--
7-- License : BSD3
8-- Maintainer : streamly@composewell.com
9-- Stability : released
10-- Portability : GHC
11--
12-- This module provides immutable arrays in pinned memory (non GC memory)
13-- suitable for long lived data storage, random access and for interfacing with
14-- the operating system.
15--
16-- Arrays in this module are chunks of pinned memory that hold a sequence of
17-- 'Storable' values of a given type, they cannot store non-serializable data
18-- like functions. Once created an array cannot be modified. Pinned memory
19-- allows efficient buffering of long lived data without adding any impact to
20-- GC. One array is just one pointer visible to GC and it does not have to be
21-- copied across generations. Moreover, pinned memory allows communication
22-- with foreign consumers and producers (e.g. file or network IO) without
23-- copying the data.
24--
25-- = Programmer Notes
26--
27-- Array creation APIs require a 'MonadIO' Monad, except 'fromList' which is a
28-- pure API. To operate on streams in pure Monads like 'Identity' you can hoist
29-- it to IO monad as follows:
30--
31-- >>> import Data.Functor.Identity (Identity, runIdentity)
32-- >>> s = Stream.fromList [1..10] :: Stream Identity Int
33-- >>> s1 = Stream.hoist (return . runIdentity) s :: Stream IO Int
34-- >>> Stream.fold Array.write s1 :: IO (Array Int)
35-- fromList [1,2,3,4,5,6,7,8,9,10]
36--
37-- 'unsafePerformIO' can be used to get a pure API from IO, as long as you know
38-- it is safe to do so:
39--
40-- >>> import System.IO.Unsafe (unsafePerformIO)
41-- >>> unsafePerformIO $ Stream.fold Array.write s1 :: Array Int
42-- fromList [1,2,3,4,5,6,7,8,9,10]
43--
44-- To apply a transformation to an array use 'read' to unfold the array into a
45-- stream, apply a transformation on the stream and then use 'write' to fold it
46-- back to an array.
47--
48-- This module is designed to be imported qualified:
49--
50-- > import qualified Streamly.Data.Array as Array
51--
52-- For experimental APIs see "Streamly.Internal.Data.Array".
54module Streamly.Data.Array.Foreign
55 {-# DEPRECATED "Please use \"Streamly.Data.Array\" instead." #-}
56 (
57 A.Array
59 -- * Arrays
60 -- ** Construction
61 -- | When performance matters, the fastest way to generate an array is
62 -- 'writeN'. 'IsList' and 'IsString' instances can be
63 -- used to conveniently construct arrays from literal values.
64 -- 'OverloadedLists' extension or 'fromList' can be used to construct an
65 -- array from a list literal. Similarly, 'OverloadedStrings' extension or
66 -- 'fromList' can be used to construct an array from a string literal.
68 -- Pure List APIs
69 , A.fromListN
70 , A.fromList
72 -- Monadic APIs
73 , A.writeN -- drop new
74 , A.write -- full buffer
75 , writeLastN -- drop old (ring buffer)
77 -- ** Elimination
78 -- 'GHC.Exts.toList' from "GHC.Exts" can be used to convert an array to a
79 -- list.
81 , A.toList
82 , A.read
83 , A.readRev
85 -- ** Casting
86 , cast
87 , asBytes
89 -- ** Random Access
90 , A.length
91 -- , (!!)
92 , A.getIndex
93 )
94where
96import Streamly.Internal.Data.Array as A
98-- $setup
99-- >>> :m
100-- >>> :set -fno-warn-deprecations
101-- >>> :set -XFlexibleContexts
102-- >>> :set -package streamly
103-- >>> import Streamly.Internal.Data.Stream (Stream)
104-- >>> import Streamly.Data.Array (Array)
105-- >>> import qualified Streamly.Internal.Data.Stream.IsStream as Stream
106-- >>> import qualified Streamly.Data.Array as Array