hybrid-vectors-0.1.2: src/Data/Vector/Hybrid/Mutable.hs
{-# LANGUAGE CPP #-}
{-# LANGUAGE GeneralizedNewtypeDeriving #-}
{-# LANGUAGE KindSignatures #-}
{-# LANGUAGE GADTs #-}
{-# LANGUAGE MultiParamTypeClasses #-}
{-# LANGUAGE UndecidableInstances #-}
{-# LANGUAGE FlexibleInstances #-}
{-# LANGUAGE TypeFamilies #-}
{-# LANGUAGE DeriveDataTypeable #-}
{-# LANGUAGE ScopedTypeVariables #-}
#ifndef MIN_VERSION_base
#define MIN_VERSION_base(x,y,z) 1
#endif
module Data.Vector.Hybrid.Mutable
( MVector
, IOVector
, STVector
-- * Accessors
-- ** Length information
, length, null
-- ** Extracting subvectors
, slice, init, tail, take, drop
, unsafeSlice, unsafeInit, unsafeTail, unsafeTake, unsafeDrop
-- ** Overlapping
, overlaps
-- * Construction
-- ** Initialisation
, new, unsafeNew, replicate, clone
-- ** Growing
, grow, unsafeGrow
-- ** Restricting memory usage
, clear
-- * Accessing individual elements
, read, write, swap
, unsafeRead, unsafeWrite, unsafeSwap
-- * Modifying vectors
-- ** Filling and copying
, set, copy, unsafeCopy
-- * Unsafe Construction and deconstruction
, unsafeZip, projectFst, projectSnd
-- * Deprecated operations
, newWith, unsafeNewWith
) where
import Control.Monad.Primitive
import qualified Data.Vector.Generic.Mutable as G
import Data.Vector.Hybrid.Internal
import Prelude hiding ( length, null, replicate, reverse, map, read, take, drop, init, tail )
type IOVector u v = MVector u v RealWorld
type STVector = MVector
-- Length information
-- ------------------
-- | Length of the mutable vector.
length :: G.MVector u a => MVector u v s (a, b) -> Int
length (MV ks _) = G.length ks
{-# INLINE length #-}
-- | Check whether the vector is empty
null :: G.MVector u a => MVector u v s (a, b) -> Bool
null (MV ks _) = G.null ks
{-# INLINE null #-}
-- Extracting subvectors
-- ---------------------
-- | Yield a part of the mutable vector without copying it.
slice :: (G.MVector u a, G.MVector v b) => Int -> Int -> MVector u v s (a, b) -> MVector u v s (a, b)
slice = G.slice
{-# INLINE slice #-}
take :: (G.MVector u a, G.MVector v b) => Int -> MVector u v s (a, b) -> MVector u v s (a, b)
take = G.take
{-# INLINE take #-}
drop :: (G.MVector u a, G.MVector v b) => Int -> MVector u v s (a, b) -> MVector u v s (a, b)
drop = G.drop
{-# INLINE drop #-}
init :: (G.MVector u a, G.MVector v b) => MVector u v s (a, b) -> MVector u v s (a, b)
init = G.init
{-# INLINE init #-}
tail :: (G.MVector u a, G.MVector v b) => MVector u v s (a, b) -> MVector u v s (a, b)
tail = G.tail
{-# INLINE tail #-}
-- | Yield a part of the mutable vector without copying it. No bounds checks
-- are performed.
unsafeSlice :: (G.MVector u a, G.MVector v b)
=> Int -- ^ starting index
-> Int -- ^ length of the slice
-> MVector u v s (a, b)
-> MVector u v s (a, b)
unsafeSlice = G.unsafeSlice
{-# INLINE unsafeSlice #-}
unsafeTake :: (G.MVector u a, G.MVector v b) => Int -> MVector u v s (a, b) -> MVector u v s (a, b)
unsafeTake = G.unsafeTake
{-# INLINE unsafeTake #-}
unsafeDrop :: (G.MVector u a, G.MVector v b) => Int -> MVector u v s (a, b) -> MVector u v s (a, b)
unsafeDrop = G.unsafeDrop
{-# INLINE unsafeDrop #-}
unsafeInit :: (G.MVector u a, G.MVector v b) => MVector u v s (a, b) -> MVector u v s (a, b)
unsafeInit = G.unsafeInit
{-# INLINE unsafeInit #-}
unsafeTail :: (G.MVector u a, G.MVector v b) => MVector u v s (a, b) -> MVector u v s (a, b)
unsafeTail = G.unsafeTail
{-# INLINE unsafeTail #-}
-- Overlapping
-- -----------
-- Check whether two vectors overlap.
overlaps :: (G.MVector u a, G.MVector v b) => MVector u v s (a, b) -> MVector u v s (a, b) -> Bool
overlaps = G.overlaps
{-# INLINE overlaps #-}
-- Initialisation
-- --------------
-- | Create a mutable vector of the given length.
new :: (PrimMonad m, G.MVector u a, G.MVector v b) => Int -> m (MVector u v (PrimState m) (a, b))
new = G.new
{-# INLINE new #-}
-- | Create a mutable vector of the given length. The length is not checked.
unsafeNew :: (PrimMonad m, G.MVector u a, G.MVector v b) => Int -> m (MVector u v (PrimState m) (a, b))
unsafeNew = G.unsafeNew
{-# INLINE unsafeNew #-}
-- | Create a mutable vector of the given length (0 if the length is negative)
-- and fill it with an initial value.
replicate :: (PrimMonad m, G.MVector u a, G.MVector v b) => Int -> (a, b) -> m (MVector u v (PrimState m) (a, b))
replicate = G.replicate
{-# INLINE replicate #-}
-- | Create a copy of a mutable vector.
clone :: (PrimMonad m, G.MVector u a, G.MVector v b)
=> MVector u v (PrimState m) (a, b) -> m (MVector u v (PrimState m) (a, b))
clone = G.clone
{-# INLINE clone #-}
-- Growing
-- -------
-- | Grow a vector by the given number of elements. The number must be
-- positive.
grow :: (PrimMonad m, G.MVector u a, G.MVector v b)
=> MVector u v (PrimState m) (a, b) -> Int -> m (MVector u v (PrimState m) (a, b))
grow = G.grow
{-# INLINE grow #-}
-- | Grow a vector by the given number of elements. The number must be
-- positive but this is not checked.
unsafeGrow :: (PrimMonad m, G.MVector u a, G.MVector v b)
=> MVector u v (PrimState m) (a, b) -> Int -> m (MVector u v (PrimState m) (a, b))
unsafeGrow = G.unsafeGrow
{-# INLINE unsafeGrow #-}
-- Restricting memory usage
-- ------------------------
-- | Reset all elements of the vector to some undefined value, clearing all
-- references to external objects. This is usually a noop for unboxed vectors.
clear :: (PrimMonad m, G.MVector u a, G.MVector v b) => MVector u v (PrimState m) (a, b) -> m ()
clear = G.clear
{-# INLINE clear #-}
-- Accessing individual elements
-- -----------------------------
-- | Yield the element at the given position.
read :: (PrimMonad m, G.MVector u a, G.MVector v b)
=> MVector u v (PrimState m) (a, b) -> Int -> m (a, b)
read = G.read
{-# INLINE read #-}
-- | Replace the element at the given position.
write :: (PrimMonad m, G.MVector u a, G.MVector v b)
=> MVector u v (PrimState m) (a, b) -> Int -> (a, b) -> m ()
write = G.write
{-# INLINE write #-}
-- | Swap the elements at the given positions.
swap :: (PrimMonad m, G.MVector u a, G.MVector v b)
=> MVector u v (PrimState m) (a, b) -> Int -> Int -> m ()
swap = G.swap
{-# INLINE swap #-}
-- | Yield the element at the given position. No bounds checks are performed.
unsafeRead :: (PrimMonad m, G.MVector u a, G.MVector v b)
=> MVector u v (PrimState m) (a, b) -> Int -> m (a, b)
unsafeRead = G.unsafeRead
{-# INLINE unsafeRead #-}
-- | Replace the element at the given position. No bounds checks are performed.
unsafeWrite :: (PrimMonad m, G.MVector u a, G.MVector v b)
=> MVector u v (PrimState m) (a, b) -> Int -> (a, b) -> m ()
unsafeWrite = G.unsafeWrite
{-# INLINE unsafeWrite #-}
-- | Swap the elements at the given positions. No bounds checks are performed.
unsafeSwap
:: (PrimMonad m, G.MVector u a, G.MVector v b)
=> MVector u v (PrimState m) (a, b) -> Int -> Int -> m ()
unsafeSwap = G.unsafeSwap
{-# INLINE unsafeSwap #-}
-- Filling and copying
-- -------------------
-- | Set all elements of the vector to the given value.
set :: (PrimMonad m, G.MVector u a, G.MVector v b)
=> MVector u v (PrimState m) (a, b) -> (a, b) -> m ()
set = G.set
{-# INLINE set #-}
-- | Copy a vector. The two vectors must have the same length and may not
-- overlap.
copy :: (PrimMonad m, G.MVector u a, G.MVector v b)
=> MVector u v (PrimState m) (a, b) -> MVector u v (PrimState m) (a, b) -> m ()
copy = G.copy
{-# INLINE copy #-}
-- | Copy a vector. The two vectors must have the same length and may not
-- overlap. This is not checked.
unsafeCopy :: (PrimMonad m, G.MVector u a, G.MVector v b)
=> MVector u v (PrimState m) (a, b) -- ^ target
-> MVector u v (PrimState m) (a, b) -- ^ source
-> m ()
{-# INLINE unsafeCopy #-}
unsafeCopy = G.unsafeCopy
-- Unsafe composition and decomposition
-- ------------------------------------
-- | The mutable vectors are assumed to be of the same length and to not overlap. This is not checked.
unsafeZip :: u s a -> v s b -> MVector u v s (a, b)
unsafeZip = MV
{-# INLINE unsafeZip #-}
projectFst :: MVector u v s (a, b) -> u s a
projectFst (MV ks _) = ks
{-# INLINE projectFst #-}
projectSnd :: MVector u v s (a, b) -> v s b
projectSnd (MV _ vs) = vs
{-# INLINE projectSnd #-}
-- Deprecated functions
-- --------------------
-- | /DEPRECATED/ Use 'replicate' instead
newWith :: (PrimMonad m, G.MVector u a, G.MVector v b) => Int -> (a, b) -> m (MVector u v (PrimState m) (a, b))
newWith = G.replicate
{-# INLINE newWith #-}
-- | /DEPRECATED/ Use 'replicate' instead
unsafeNewWith :: (PrimMonad m, G.MVector u a, G.MVector v b) => Int -> (a, b) -> m (MVector u v (PrimState m) (a, b))
unsafeNewWith = G.replicate
{-# INLINE unsafeNewWith #-}
{-# DEPRECATED newWith, unsafeNewWith "Use replicate instead" #-}