{-# OPTIONS_HADDOCK hide #-} {-# LANGUAGE CPP #-} #include "fusion-phases.h" -- | Definition of the PRepr/PA family and class. -- This module manages the conversion between the user level view of the -- element data, and our internal generic view. module Data.Array.Parallel.PArray.PRepr.Base ( PRepr , PA (..) , toNestedArrPRepr -- * House Keeping , validPA , nfPA , similarPA , coversPA , pprpPA , pprpDataPA -- * Constructors , emptyPA , replicatePA, replicatesPA , appendPA, appendsPA -- * Projections , lengthPA , indexPA, indexsPA, indexvsPA , bpermutePA , extractPA, extractssPA, extractvsPA -- * Pack and Combine , packByTagPA , combine2PA -- * Conversions , fromVectorPA, toVectorPA -- * PDatas , emptydPA , singletondPA , lengthdPA , indexdPA , appenddPA , fromVectordPA, toVectordPA) where import Data.Array.Parallel.Pretty import Data.Array.Parallel.PArray.PData.Base import Data.Array.Parallel.PArray.PData.Nested import Data.Array.Parallel.Base (Tag) import Data.Vector (Vector) import qualified Data.Array.Parallel.Unlifted as U import qualified Data.Vector as V -- PRepr / PA ----------------------------------------------------------------- -- | Family of Representable types. These are the types that we know how to -- represent generically. `PRepr` takes an arbitrary type and produces the -- generic type we use to represent it. -- -- Instances for simple types are defined by the library. -- For algebraic types, it's up to the vectoriser/client module to create -- a suitable instance. -- type family PRepr a -- | A PA dictionary contains the functions that we use to convert a -- representable type to and from its generic representation. -- -- The conversions methods should all be O(1). class PR (PRepr a) => PA a where toPRepr :: a -> PRepr a fromPRepr :: PRepr a -> a toArrPRepr :: PData a -> PData (PRepr a) fromArrPRepr :: PData (PRepr a) -> PData a toArrPReprs :: PDatas a -> PDatas (PRepr a) fromArrPReprs :: PDatas (PRepr a) -> PDatas a -- | Convert a nested array to its generic representation. toNestedArrPRepr :: PA a => PData (PArray a) -> PData (PArray (PRepr a)) toNestedArrPRepr (PNested vsegd pdatas segd flat) = PNested vsegd (toArrPReprs pdatas) segd (toArrPRepr flat) -- PA Wrappers ---------------------------------------------------------------- -- These wrappers work on (PData a) arrays when we know the element type 'a' -- is generically representable. We implement the array operators by converting -- the PData to our generic representation type, and use the corresponding -- method from the PR dictionary. -- -- The wrappers are used in situations when we only have PA dictionary, -- instead of a PR dictionary. This happens in the PR (a :-> b) instance, -- as we need to work on a generically represented environment, and only -- have an existential PA dictionary. We also use them in the PA functions -- defined by D.A.P.PArray. -- -- See the D.A.P.PArray.PData.Base for docs on what these functions do. -- Each of the following functions has a corresponding method in the PR class. -- {-# INLINE_PA validPA #-} validPA :: PA a => PData a -> Bool validPA arr = validPR (toArrPRepr arr) {-# INLINE_PA nfPA #-} nfPA :: PA a => PData a -> () nfPA arr = nfPR $ toArrPRepr arr {-# INLINE_PA similarPA #-} similarPA :: PA a => a -> a -> Bool similarPA x y = similarPR (toPRepr x) (toPRepr y) {-# INLINE_PA coversPA #-} coversPA :: PA a => Bool -> PData a -> Int -> Bool coversPA weak pdata ix = coversPR weak (toArrPRepr pdata) ix {-# INLINE_PA pprpPA #-} pprpPA :: PA a => a -> Doc pprpPA x = pprpPR (toPRepr x) {-# INLINE_PA pprpDataPA #-} pprpDataPA :: PA a => PData a -> Doc pprpDataPA x = pprpDataPR (toArrPRepr x) -- Constructors --------------------------------- {-# INLINE_PA emptyPA #-} emptyPA :: PA a => PData a emptyPA = fromArrPRepr emptyPR {-# INLINE_PA replicatePA #-} replicatePA :: PA a => Int -> a -> PData a replicatePA n x = fromArrPRepr $ replicatePR n $ toPRepr x {-# INLINE_PA replicatesPA #-} replicatesPA :: PA a => U.Segd -> PData a -> PData a replicatesPA segd xs = fromArrPRepr $ replicatesPR segd (toArrPRepr xs) {-# INLINE_PA appendPA #-} appendPA :: PA a => PData a -> PData a -> PData a appendPA xs ys = fromArrPRepr $ appendPR (toArrPRepr xs) (toArrPRepr ys) {-# INLINE_PA appendsPA #-} appendsPA :: PA a => U.Segd -> U.Segd -> PData a -> U.Segd -> PData a -> PData a appendsPA segdResult segd1 xs segd2 ys = fromArrPRepr $ appendsPR segdResult segd1 (toArrPRepr xs) segd2 (toArrPRepr ys) -- Projections ---------------------------------- {-# INLINE_PA lengthPA #-} lengthPA :: PA a => PData a -> Int lengthPA xs = lengthPR (toArrPRepr xs) {-# INLINE_PA indexPA #-} indexPA :: PA a => PData a -> Int -> a indexPA xs i = fromPRepr $ indexPR (toArrPRepr xs) i {-# INLINE_PA indexsPA #-} indexsPA :: PA a => PDatas a -> U.Array (Int, Int) -> PData a indexsPA pdatas srcixs = fromArrPRepr $ indexsPR (toArrPReprs pdatas) srcixs {-# INLINE_PA indexvsPA #-} indexvsPA :: PA a => PDatas a -> U.VSegd -> U.Array (Int, Int) -> PData a indexvsPA pdatas vsegd srcixs = fromArrPRepr $ indexvsPR (toArrPReprs pdatas) vsegd srcixs {-# INLINE_PDATA bpermutePA #-} bpermutePA :: PA a => PData a -> U.Array Int -> PData a bpermutePA xs ixs = fromArrPRepr $ bpermutePR (toArrPRepr xs) ixs {-# INLINE_PA extractPA #-} extractPA :: PA a => PData a -> Int -> Int -> PData a extractPA xs start len = fromArrPRepr $ extractPR (toArrPRepr xs) start len {-# INLINE_PA extractssPA #-} extractssPA :: PA a => PDatas a -> U.SSegd -> PData a extractssPA xss segd = fromArrPRepr $ extractssPR (toArrPReprs xss) segd {-# INLINE_PA extractvsPA #-} extractvsPA :: PA a => PDatas a -> U.VSegd -> PData a extractvsPA xss segd = fromArrPRepr $ extractvsPR (toArrPReprs xss) segd -- Pack and Combine ----------------------------- {-# INLINE_PA packByTagPA #-} packByTagPA :: PA a => PData a -> U.Array Tag -> Tag -> PData a packByTagPA xs tags tag = fromArrPRepr $ packByTagPR (toArrPRepr xs) tags tag {-# INLINE_PA combine2PA #-} combine2PA :: PA a => U.Sel2 -> PData a -> PData a -> PData a combine2PA sel xs ys = fromArrPRepr $ combine2PR sel (toArrPRepr xs) (toArrPRepr ys) -- Conversions ---------------------------------- {-# INLINE_PA fromVectorPA #-} fromVectorPA :: PA a => Vector a -> PData a fromVectorPA vec = fromArrPRepr $ fromVectorPR (V.map toPRepr vec) {-# INLINE_PA toVectorPA #-} toVectorPA :: PA a => PData a -> Vector a toVectorPA pdata = V.map fromPRepr $ toVectorPR (toArrPRepr pdata) {-# INLINE_PA emptydPA #-} emptydPA :: PA a => PDatas a emptydPA = fromArrPReprs $ emptydPR {-# INLINE_PA singletondPA #-} singletondPA :: PA a => PData a -> PDatas a singletondPA pdata = fromArrPReprs $ singletondPR (toArrPRepr pdata) {-# INLINE_PA lengthdPA #-} lengthdPA :: PA a => PDatas a -> Int lengthdPA pdatas = lengthdPR (toArrPReprs pdatas) {-# INLINE_PA indexdPA #-} indexdPA :: PA a => PDatas a -> Int -> PData a indexdPA pdatas ix = fromArrPRepr $ indexdPR (toArrPReprs pdatas) ix {-# INLINE_PA appenddPA #-} appenddPA :: PA a => PDatas a -> PDatas a -> PDatas a appenddPA xs ys = fromArrPReprs $ appenddPR (toArrPReprs xs) (toArrPReprs ys) {-# INLINE_PA fromVectordPA #-} fromVectordPA :: PA a => V.Vector (PData a) -> PDatas a fromVectordPA vec = fromArrPReprs $ fromVectordPR (V.map toArrPRepr vec) {-# INLINE_PA toVectordPA #-} toVectordPA :: PA a => PDatas a -> V.Vector (PData a) toVectordPA pdatas = V.map fromArrPRepr $ toVectordPR (toArrPReprs pdatas)