module Data.RangeMin.Common.Vector (vec, unsafeVec, unsafeBackpermute', enumFromN, foldlRange, replicateM, inlineCreate,
inlineUnstream, inlineUnstreamR, inlineBuild, hintSize, module Data.RangeMin.Common.Vector.Utils,
streamI, streamIR) where
import Control.Monad hiding (replicateM)
import Data.RangeMin.Common.ST
import Data.RangeMin.Common.Types
import qualified Data.Vector.Generic as G
import qualified Data.Vector.Generic.Mutable as GM
import qualified Data.Vector.Generic.New as New
import qualified Data.Vector.Fusion.Stream as S
import Data.RangeMin.Common.Vector.Utils
import Data.Vector.Fusion.Stream.Size
import Control.Monad.Primitive
import Prelude hiding (drop, read)
hintSize :: Vector v a => Int -> v a -> v a
hintSize n xs = G.unstream (G.stream xs `S.sized` Exact n)
inlineCreate :: Vector v a => (forall s . ST s (Mutable v s a)) -> v a
inlineCreate m = inlineNew (New.New m)
replicateM :: (Vector v a, PrimMonad m) => Int -> m a -> m (v a)
replicateM !n x = do
!arr <- new n
forM_ [0..n1] $ \ i -> write arr i =<< x
unsafeFreeze arr
foldlRange :: (Int -> Int -> Int) -> Int -> Int -> Int
foldlRange f !i !n = S.foldl1' f (enumFromN i n)
unsafeVec :: Vector v Int => Int -> S.Stream IP -> v Int
unsafeVec !n str = inlineCreate $ do
!vec <- new n
S.mapM_ (\ (IP i x) -> write vec i x) str
return vec
enumFromN :: Int -> Int -> S.Stream Int
enumFromN !i !n = S.unfoldr suc i `S.sized` Exact n where
!end = i + n
suc i | i >= end = Nothing
| otherwise = Just (i, i+1)
inlineUnstream :: Vector v a => S.Stream a -> v a
inlineUnstream s = inlineNew (New.unstream s)
inlineUnstreamR :: Vector v a => S.Stream a -> v a
inlineUnstreamR s = inlineNew (New.unstreamR s)
inlineNew :: Vector v a => New.New v a -> v a
inlineNew !m = inlineRunST (unsafeFreeze =<< New.run m)
streamI :: Vector v a => v a -> S.Stream (Int, a)
streamI !xs = S.generate (G.length xs) (\ i -> (i, xs ! i))
streamIR :: Vector v a => v a -> S.Stream (Int, a)
streamIR !xs = S.unfoldr suc n `S.sized` Exact n where
!n = G.length xs
suc i = if i == 0 then Nothing else let
!i' = i 1
xi' = xs ! i'
in Just ((i', xi'), i')
inlineBuild :: Vector v a => v a -> v a
inlineBuild xs = inlineUnstream (G.stream xs)
vec :: Vector v a => Int -> S.Stream (Int, a) -> v a
vec !n str = G.create $ do
vec <- new n
GM.update vec str
return vec
unsafeBackpermute' :: (Vector v a, Vector v' Int) => v a -> v' Int -> v a
unsafeBackpermute' !v is = inlineUnstream
$ S.unbox
$ S.map (G.unsafeIndexM v)
$ G.stream is