module Data.Array.Comfort.Storable.Mutable ( Array, MutArray.STArray, MutArray.IOArray, shape, MutArray.new, read, write, update, toList, fromList, vectorFromList, MutArray.thaw, MutArray.freeze, ) where import qualified Data.Array.Comfort.Storable.Mutable.Unchecked as MutArray import qualified Data.Array.Comfort.Shape as Shape import Data.Array.Comfort.Storable.Mutable.Unchecked (Array) import Foreign.Marshal.Array (pokeArray) import Foreign.Storable (Storable) import Control.Monad.Primitive (PrimMonad) import Prelude hiding (read) shape :: Array m sh a -> sh shape = MutArray.shape read :: (PrimMonad m, Shape.Indexed sh, Storable a) => Array m sh a -> Shape.Index sh -> m a read arr ix = if Shape.inBounds (shape arr) ix then MutArray.read arr ix else error "Array.Comfort.Storable.Mutable.read: index out of bounds" write :: (PrimMonad m, Shape.Indexed sh, Storable a) => Array m sh a -> Shape.Index sh -> a -> m () write arr ix a = if Shape.inBounds (shape arr) ix then MutArray.write arr ix a else error "Array.Comfort.Storable.Mutable.write: index out of bounds" update :: (PrimMonad m, Shape.Indexed sh, Storable a) => Array m sh a -> Shape.Index sh -> (a -> a) -> m () update arr ix f = if Shape.inBounds (shape arr) ix then MutArray.update arr ix f else error "Array.Comfort.Storable.Mutable.update: index out of bounds" toList :: (PrimMonad m, Shape.C sh, Storable a) => Array m sh a -> m [a] toList = MutArray.toList fromList :: (PrimMonad m, Shape.C sh, Storable a) => sh -> [a] -> m (Array m sh a) fromList sh xs = MutArray.unsafeCreateWithSize sh $ \size ptr -> pokeArray ptr $ take size $ xs ++ repeat (error "Array.Comfort.Storable.fromList: list too short for shape") vectorFromList :: (PrimMonad m, Storable a) => [a] -> m (Array m (Shape.ZeroBased Int) a) vectorFromList = MutArray.vectorFromList