-- Hoogle documentation, generated by Haddock
-- See Hoogle, http://www.haskell.org/hoogle/


-- | Utility functions for the Accelerate framework
--   
--   Several utility functions on top of the Accelerate framework. The
--   functions simplify working with indices and lifting and unlifting.
@package accelerate-utility
@version 1.0.0.1

module Data.Array.Accelerate.Utility.Arrange
mapWithIndex :: (Shape sh, Elt a, Elt b) => (Exp sh -> Exp a -> Exp b) -> Acc (Array sh a) -> Acc (Array sh b)
gather :: (Shape ix, Shape ix', Elt ix', Elt a) => Acc (Array ix ix') -> Acc (Array ix' a) -> Acc (Array ix a)
scatter :: (Shape ix, Shape ix', Elt ix', Elt a) => (Exp a -> Exp a -> Exp a) -> Acc (Array ix ix') -> Acc (Array ix' a) -> Acc (Array ix a) -> Acc (Array ix' a)

module Data.Array.Accelerate.Utility.Lift.Exp

-- | This class simplifies untupling of expressions. If you have a function
--   
--   <pre>
--   g :: ((Exp a, Exp b), Exp (c,d)) -&gt; (Exp e, Exp f)
--   </pre>
--   
--   you cannot apply it to an array <tt>arr :: Array sh ((a,b),(c,d))</tt>
--   using <a>map</a>. Here, the <a>modify</a> function helps:
--   
--   <pre>
--   modify ((expr,expr),expr) g :: Exp ((a,b),(c,d)) -&gt; Exp (e,f)
--   </pre>
--   
--   The <a>expr</a>-pattern tells, how deep the tuple shall be unlifted.
--   This way you can write:
--   
--   <pre>
--   A.map
--      (Exp.modify ((expr,expr),expr) $ \((a,b), cd) -&gt; g ((a,b), cd))
--      arr
--   </pre>
--   
--   <a>modify</a> is based on <a>unlift</a>. In contrast to <a>unlift</a>
--   it does not only unlift one level of tupels, but is guided by an
--   <a>expr</a>-pattern. In the example I have demonstrated, how the pair
--   <tt>(a,b)</tt> is unlifted, but the pair <tt>(c,d)</tt> is not. For
--   the result tuple, <a>modify</a> simply calls <a>lift</a>. In contrast
--   to <a>unlift</a>, <a>lift</a> lifts over all tupel levels until it
--   obtains a single <a>Exp</a>.
class (Elt (Tuple pattern), Plain (Unlifted pattern) ~ Tuple pattern) => Unlift pattern where {
    type family Unlifted pattern;
    type family Tuple pattern;
}
unlift :: Unlift pattern => pattern -> Exp (Tuple pattern) -> Unlifted pattern
unlift :: Unlift pattern => pattern -> Exp (Tuple pattern) -> Unlifted pattern
modify :: (Lift Exp a, Unlift pattern) => pattern -> (Unlifted pattern -> a) -> Exp (Tuple pattern) -> Exp (Plain a)
modify2 :: (Lift Exp a, Unlift patternA, Unlift patternB) => patternA -> patternB -> (Unlifted patternA -> Unlifted patternB -> a) -> Exp (Tuple patternA) -> Exp (Tuple patternB) -> Exp (Plain a)
modify3 :: (Lift Exp a, Unlift patternA, Unlift patternB, Unlift patternC) => patternA -> patternB -> patternC -> (Unlifted patternA -> Unlifted patternB -> Unlifted patternC -> a) -> Exp (Tuple patternA) -> Exp (Tuple patternB) -> Exp (Tuple patternC) -> Exp (Plain a)
modify4 :: (Lift Exp a, Unlift patternA, Unlift patternB, Unlift patternC, Unlift patternD) => patternA -> patternB -> patternC -> patternD -> (Unlifted patternA -> Unlifted patternB -> Unlifted patternC -> Unlifted patternD -> a) -> Exp (Tuple patternA) -> Exp (Tuple patternB) -> Exp (Tuple patternC) -> Exp (Tuple patternD) -> Exp (Plain a)
data Exp e
Exp :: Exp e
expr :: Exp e

-- | for compatibility with accelerate-utility-0.0

-- | <i>Deprecated: use expr instead</i>
atom :: Exp e
unliftPair :: (Elt a, Elt b) => Exp (a, b) -> (Exp a, Exp b)
unliftTriple :: (Elt a, Elt b, Elt c) => Exp (a, b, c) -> (Exp a, Exp b, Exp c)
unliftQuadruple :: (Elt a, Elt b, Elt c, Elt d) => Exp (a, b, c, d) -> (Exp a, Exp b, Exp c, Exp d)
asExp :: Exp a -> Exp a
mapFst :: (Elt a, Elt b, Elt c) => (Exp a -> Exp b) -> Exp (a, c) -> Exp (b, c)
mapSnd :: (Elt a, Elt b, Elt c) => (Exp b -> Exp c) -> Exp (a, b) -> Exp (a, c)
fst3 :: (Elt a, Elt b, Elt c) => Exp (a, b, c) -> Exp a
snd3 :: (Elt a, Elt b, Elt c) => Exp (a, b, c) -> Exp b
thd3 :: (Elt a, Elt b, Elt c) => Exp (a, b, c) -> Exp c
indexCons :: (Slice ix) => Exp ix -> Exp Int -> Exp (ix :. Int)
instance Data.Array.Accelerate.Array.Sugar.Elt a => Data.Array.Accelerate.Utility.Lift.Exp.Unlift (Data.Array.Accelerate.Utility.Lift.Exp.Exp a)
instance (Data.Array.Accelerate.Utility.Lift.Exp.Unlift pa, Data.Array.Accelerate.Array.Sugar.Slice (Data.Array.Accelerate.Utility.Lift.Exp.Tuple pa), int ~ Data.Array.Accelerate.Utility.Lift.Exp.Exp GHC.Types.Int) => Data.Array.Accelerate.Utility.Lift.Exp.Unlift (pa Data.Array.Accelerate.Array.Sugar.:. int)
instance (Data.Array.Accelerate.Utility.Lift.Exp.Unlift pa, Data.Array.Accelerate.Utility.Lift.Exp.Unlift pb) => Data.Array.Accelerate.Utility.Lift.Exp.Unlift (pa, pb)
instance (Data.Array.Accelerate.Utility.Lift.Exp.Unlift pa, Data.Array.Accelerate.Utility.Lift.Exp.Unlift pb, Data.Array.Accelerate.Utility.Lift.Exp.Unlift pc) => Data.Array.Accelerate.Utility.Lift.Exp.Unlift (pa, pb, pc)
instance Data.Array.Accelerate.Utility.Lift.Exp.Unlift p => Data.Array.Accelerate.Utility.Lift.Exp.Unlift (Data.Complex.Complex p)

module Data.Array.Accelerate.Utility.Lift.Acc

-- | This class is like <a>Unlift</a> but for the <a>Acc</a> environment.
--   It allows you to unlift an <a>Acc</a> of nested tuples into tuples of
--   <a>Exp</a> and <a>Acc</a> values. It can be quite handy when working
--   with <a>acond</a> and <a>awhile</a>. It can also be useful in
--   connection with running an <tt>accelerate</tt> algorithm at a certain
--   backend, like <a>run1</a>. But in this case you might prefer
--   <a>Data.Array.Accelerate.Utility.Lift.Run</a>.
class (Arrays (Tuple pattern)) => Unlift pattern where {
    type family Unlifted pattern;
    type family Tuple pattern;
}
unlift :: Unlift pattern => pattern -> Acc (Tuple pattern) -> Unlifted pattern
unlift :: Unlift pattern => pattern -> Acc (Tuple pattern) -> Unlifted pattern
modify :: (Lift Acc a, Unlift pattern) => pattern -> (Unlifted pattern -> a) -> Acc (Tuple pattern) -> Acc (Plain a)
modify2 :: (Lift Acc a, Unlift patternA, Unlift patternB) => patternA -> patternB -> (Unlifted patternA -> Unlifted patternB -> a) -> Acc (Tuple patternA) -> Acc (Tuple patternB) -> Acc (Plain a)
modify3 :: (Lift Acc a, Unlift patternA, Unlift patternB, Unlift patternC) => patternA -> patternB -> patternC -> (Unlifted patternA -> Unlifted patternB -> Unlifted patternC -> a) -> Acc (Tuple patternA) -> Acc (Tuple patternB) -> Acc (Tuple patternC) -> Acc (Plain a)
modify4 :: (Lift Acc a, Unlift patternA, Unlift patternB, Unlift patternC, Unlift patternD) => patternA -> patternB -> patternC -> patternD -> (Unlifted patternA -> Unlifted patternB -> Unlifted patternC -> Unlifted patternD -> a) -> Acc (Tuple patternA) -> Acc (Tuple patternB) -> Acc (Tuple patternC) -> Acc (Tuple patternD) -> Acc (Plain a)
data Acc a
Acc :: Acc a
acc :: Acc a
data Exp e
Exp :: Exp e
expr :: Exp e
unliftPair :: (Arrays a, Arrays b) => Acc (a, b) -> (Acc a, Acc b)
unliftTriple :: (Arrays a, Arrays b, Arrays c) => Acc (a, b, c) -> (Acc a, Acc b, Acc c)
unliftQuadruple :: (Arrays a, Arrays b, Arrays c, Arrays d) => Acc (a, b, c, d) -> (Acc a, Acc b, Acc c, Acc d)
mapFst :: (Arrays a, Arrays b, Arrays c) => (Acc a -> Acc b) -> Acc (a, c) -> Acc (b, c)
mapSnd :: (Arrays a, Arrays b, Arrays c) => (Acc b -> Acc c) -> Acc (a, b) -> Acc (a, c)

-- | like <a>unit</a> in the <a>Acc</a> environment
singleton :: (Elt e) => e -> Scalar e

-- | like <a>the</a> in the <a>Acc</a> environment
the :: (Elt e) => Scalar e -> e
instance Data.Array.Accelerate.Array.Sugar.Arrays a => Data.Array.Accelerate.Utility.Lift.Acc.Unlift (Data.Array.Accelerate.Utility.Lift.Acc.Acc a)
instance Data.Array.Accelerate.Array.Sugar.Elt a => Data.Array.Accelerate.Utility.Lift.Acc.Unlift (Data.Array.Accelerate.Utility.Lift.Exp.Exp a)
instance (Data.Array.Accelerate.Utility.Lift.Acc.Unlift pa, Data.Array.Accelerate.Utility.Lift.Acc.Unlift pb) => Data.Array.Accelerate.Utility.Lift.Acc.Unlift (pa, pb)
instance (Data.Array.Accelerate.Utility.Lift.Acc.Unlift pa, Data.Array.Accelerate.Utility.Lift.Acc.Unlift pb, Data.Array.Accelerate.Utility.Lift.Acc.Unlift pc) => Data.Array.Accelerate.Utility.Lift.Acc.Unlift (pa, pb, pc)


-- | Simplify running <tt>accelerate</tt> functions with multiple curried
--   array and expression arguments.
module Data.Array.Accelerate.Utility.Lift.Run

-- | If you have a function:
--   
--   <pre>
--   f :: Exp a -&gt; (Acc b, Acc c) -&gt; (Acc d, Acc e)
--   </pre>
--   
--   you cannot run this immediately using <a>run1</a>, since <tt>run1</tt>
--   expects a function with a single <a>Acc</a> parameter and a single
--   <a>Acc</a> result. Using the <a>with</a> function you can just run
--   <tt>f</tt> as is:
--   
--   <pre>
--   with run1 f :: a -&gt; (b,c) -&gt; (d,e)
--   </pre>
class C f where {
    type family Arguments a f;
    type family Result f;
    type family Plain f;
}
with1 :: (C f, (Arrays a)) => ((Acc (Arguments a f) -> Acc (Result f)) -> (Arguments a f -> Result f)) -> (Acc a -> f) -> a -> Plain f
with :: (C f) => ((Acc (Arguments () f) -> Acc (Result f)) -> (Arguments () f -> Result f)) -> f -> Plain f
class (Arrays (Packed a)) => Argument a where {
    type family Packed a;
    type family Unpacked a;
}
tunnel :: Argument a => (Unpacked a -> Packed a, Acc (Packed a) -> a)
instance (Data.Array.Accelerate.Utility.Lift.Run.Argument arg, Data.Array.Accelerate.Utility.Lift.Run.C f) => Data.Array.Accelerate.Utility.Lift.Run.C (arg -> f)
instance Data.Array.Accelerate.Array.Sugar.Arrays a => Data.Array.Accelerate.Utility.Lift.Run.Argument (Data.Array.Accelerate.Smart.Acc a)
instance Data.Array.Accelerate.Array.Sugar.Elt a => Data.Array.Accelerate.Utility.Lift.Run.Argument (Data.Array.Accelerate.Smart.Exp a)
instance (Data.Array.Accelerate.Utility.Lift.Run.Argument a, Data.Array.Accelerate.Utility.Lift.Run.Argument b) => Data.Array.Accelerate.Utility.Lift.Run.Argument (a, b)
instance (Data.Array.Accelerate.Utility.Lift.Run.Argument a, Data.Array.Accelerate.Utility.Lift.Run.Argument b, Data.Array.Accelerate.Utility.Lift.Run.Argument c) => Data.Array.Accelerate.Utility.Lift.Run.Argument (a, b, c)
instance Data.Array.Accelerate.Utility.Lift.Run.Argument Data.Array.Accelerate.Array.Sugar.Z
instance (Data.Array.Accelerate.Lift.Unlift Data.Array.Accelerate.Smart.Exp a, Data.Array.Accelerate.Lift.Lift Data.Array.Accelerate.Smart.Exp a, Data.Array.Accelerate.Array.Sugar.Slice (Data.Array.Accelerate.Lift.Plain a), b ~ Data.Array.Accelerate.Smart.Exp GHC.Types.Int) => Data.Array.Accelerate.Utility.Lift.Run.Argument (a Data.Array.Accelerate.Array.Sugar.:. b)
instance Data.Array.Accelerate.Utility.Lift.Run.C (Data.Array.Accelerate.Smart.Acc r)
instance (Data.Array.Accelerate.Lift.Lift Data.Array.Accelerate.Smart.Acc r, Data.Array.Accelerate.Array.Sugar.Arrays (Data.Array.Accelerate.Lift.Plain r), Data.Array.Accelerate.Lift.Lift Data.Array.Accelerate.Smart.Acc s, Data.Array.Accelerate.Array.Sugar.Arrays (Data.Array.Accelerate.Lift.Plain s)) => Data.Array.Accelerate.Utility.Lift.Run.C (r, s)
instance (Data.Array.Accelerate.Lift.Lift Data.Array.Accelerate.Smart.Acc r, Data.Array.Accelerate.Array.Sugar.Arrays (Data.Array.Accelerate.Lift.Plain r), Data.Array.Accelerate.Lift.Lift Data.Array.Accelerate.Smart.Acc s, Data.Array.Accelerate.Array.Sugar.Arrays (Data.Array.Accelerate.Lift.Plain s), Data.Array.Accelerate.Lift.Lift Data.Array.Accelerate.Smart.Acc t, Data.Array.Accelerate.Array.Sugar.Arrays (Data.Array.Accelerate.Lift.Plain t)) => Data.Array.Accelerate.Utility.Lift.Run.C (r, s, t)

module Data.Array.Accelerate.Utility.Loop
nest :: (Arrays a) => Exp Int -> (Acc a -> Acc a) -> Acc a -> Acc a
nestLog2 :: (Arrays a) => Exp Int -> (Acc a -> Acc a) -> Acc a -> Acc a

module Data.Array.Accelerate.Utility.Ord
argmin :: (Elt a, Elt b, Ord a) => Exp (a, b) -> Exp (a, b) -> Exp (a, b)
argminimum :: (Slice sh, Shape sh, Elt a, Elt b, Ord a) => Acc (Array sh (a, b)) -> Acc (Scalar (a, b))
argmax :: (Elt a, Elt b, Ord a) => Exp (a, b) -> Exp (a, b) -> Exp (a, b)
argmaximum :: (Slice sh, Shape sh, Elt a, Elt b, Ord a) => Acc (Array sh (a, b)) -> Acc (Scalar (a, b))


-- | An alternative Shape class that allows to add new "methods", but
--   forbids to add new instances. You can provide new "methods" by calling
--   <a>switch</a> with a newtype around your function type.
--   
--   For the general concept, see:
--   <a>https://www.haskell.org/haskellwiki/Closed_world_instances</a>
module Data.Array.Accelerate.Utility.Shape
class (Shape sh, Slice sh, Elt sh, Eq sh, Plain sh ~ sh, Lift Exp sh) => C sh
switch :: C sh => f Z -> (forall sh0. C sh0 => f (sh0 :. Int)) -> f sh
instance Data.Array.Accelerate.Utility.Shape.C Data.Array.Accelerate.Array.Sugar.Z
instance (Data.Array.Accelerate.Utility.Shape.C sh, i ~ GHC.Types.Int) => Data.Array.Accelerate.Utility.Shape.C (sh Data.Array.Accelerate.Array.Sugar.:. i)


-- | List-like functions on the inner dimension.
module Data.Array.Accelerate.Utility.Sliced
length :: (Shape sh, Slice sh, Elt a) => Acc (Array (sh :. Int) a) -> Exp Int
head :: (Shape sh, Slice sh, Elt a) => Acc (Array (sh :. Int) a) -> Acc (Array sh a)
tail :: (Shape sh, Slice sh, Elt a) => Acc (Array (sh :. Int) a) -> Acc (Array (sh :. Int) a)
cons :: (Shape sh, Slice sh, Elt a) => Acc (Array sh a) -> Acc (Array (sh :. Int) a) -> Acc (Array (sh :. Int) a)
consExp :: (Shape sh, Slice sh, Elt a) => Exp a -> Acc (Array (sh :. Int) a) -> Acc (Array (sh :. Int) a)
append3 :: (Shape sh, Slice sh, Elt a) => Acc (Array (sh :. Int) a) -> Acc (Array (sh :. Int) a) -> Acc (Array (sh :. Int) a) -> Acc (Array (sh :. Int) a)
stack3 :: (Shape sh, Slice sh, Elt a) => Acc (Array (sh :. Int) a) -> Acc (Array (sh :. Int) a) -> Acc (Array (sh :. Int) a) -> Acc (Array ((sh :. Int) :. Int) a)
take :: (Shape sh, Slice sh, Elt a) => Exp Int -> Acc (Array (sh :. Int) a) -> Acc (Array (sh :. Int) a)
drop :: (Shape sh, Slice sh, Elt a) => Exp Int -> Acc (Array (sh :. Int) a) -> Acc (Array (sh :. Int) a)
pad :: (Shape sh, Slice sh, Elt a) => Exp a -> Exp Int -> Acc (Array (sh :. Int) a) -> Acc (Array (sh :. Int) a)

-- | <tt>sliceVertical</tt> would be a simple <a>reshape</a>.
sliceHorizontal :: (Shape sh, Slice sh, Elt a) => Exp DIM2 -> Acc (Array (sh :. Int) a) -> Acc (Array ((sh :. Int) :. Int) a)
sieve :: (Shape sh, Slice sh, Elt a) => Exp Int -> Exp Int -> Acc (Array (sh :. Int) a) -> Acc (Array (sh :. Int) a)


-- | List-like functions on the next-to-innermost dimension.
module Data.Array.Accelerate.Utility.Sliced1
length :: (Shape sh, Slice sh, Elt a) => Acc (Array ((sh :. Int) :. Int) a) -> Exp Int
head :: (Shape sh, Slice sh, Elt a) => Acc (Array ((sh :. Int) :. Int) a) -> Acc (Array (sh :. Int) a)
tail :: (Shape sh, Slice sh, Elt a) => Acc (Array ((sh :. Int) :. Int) a) -> Acc (Array ((sh :. Int) :. Int) a)
cons :: (Shape sh, Slice sh, Elt a) => Acc (Array (sh :. Int) a) -> Acc (Array ((sh :. Int) :. Int) a) -> Acc (Array ((sh :. Int) :. Int) a)

-- | The outer and innermost dimensions must match. Otherwise you may or
--   may not get out-of-bound errors.
append :: (Shape sh, Slice sh, Elt a) => Acc (Array ((sh :. Int) :. Int) a) -> Acc (Array ((sh :. Int) :. Int) a) -> Acc (Array ((sh :. Int) :. Int) a)
append3 :: (Shape sh, Slice sh, Elt a) => Acc (Array ((sh :. Int) :. Int) a) -> Acc (Array ((sh :. Int) :. Int) a) -> Acc (Array ((sh :. Int) :. Int) a) -> Acc (Array ((sh :. Int) :. Int) a)
stack3 :: (Shape sh, Slice sh, Elt a) => Acc (Array ((sh :. Int) :. Int) a) -> Acc (Array ((sh :. Int) :. Int) a) -> Acc (Array ((sh :. Int) :. Int) a) -> Acc (Array (((sh :. Int) :. Int) :. Int) a)
take :: (Shape sh, Slice sh, Elt a) => Exp Int -> Acc (Array ((sh :. Int) :. Int) a) -> Acc (Array ((sh :. Int) :. Int) a)
drop :: (Shape sh, Slice sh, Elt a) => Exp Int -> Acc (Array ((sh :. Int) :. Int) a) -> Acc (Array ((sh :. Int) :. Int) a)
sieve :: (Shape sh, Slice sh, Elt a) => Exp Int -> Exp Int -> Acc (Array ((sh :. Int) :. Int) a) -> Acc (Array ((sh :. Int) :. Int) a)
