Haddock comments
authorRoman Leshchinskiy <rl@cse.unsw.edu.au>
Sat, 12 Jul 2008 03:44:26 +0000 (03:44 +0000)
committerRoman Leshchinskiy <rl@cse.unsw.edu.au>
Sat, 12 Jul 2008 03:44:26 +0000 (03:44 +0000)
Data/Vector/IVector.hs
Data/Vector/MVector.hs
Data/Vector/Stream.hs
Data/Vector/Stream/Size.hs
Data/Vector/Unboxed/Unbox.hs

index ee5d655..7b072f3 100644 (file)
@@ -1,9 +1,52 @@
-{-# LANGUAGE Rank2Types, MultiParamTypeClasses, BangPatterns, CPP #-}
+{-# LANGUAGE Rank2Types, MultiParamTypeClasses #-}
+-- |
+-- Module      : Data.Vector.IVector
+-- Copyright   : (c) Roman Leshchinskiy 2008
+-- License     : BSD-style
+--
+-- Maintainer  : rl@cse.unsw.edu.au
+-- Stability   : experimental
+-- Portability : non-portable
+-- 
+-- Generic interface to pure vectors
+--
 
 #include "phases.h"
 
 
 #include "phases.h"
 
-module Data.Vector.IVector
-where
+module Data.Vector.IVector (
+  -- * Immutable vectors
+  IVector,
+
+  -- * Length information
+  length,
+
+  -- * Construction
+  empty, singleton, cons, snoc, replicate, (++),
+
+  -- * Subvectors
+  take, drop,
+
+  -- * Mapping and zipping
+  map, zipWith,
+
+  -- * Filtering
+  filter, takeWhile, dropWhile,
+
+  -- * Folding
+ foldl, foldl1, foldl', foldl1', foldr, foldr1,
+
+  -- * Conversion to/from lists
+  toList, fromList,
+
+  -- * Conversion to/from Streams
+  stream, unstream,
+
+  -- * MVector-based initialisation
+  create,
+
+  -- * Unsafe functions
+  unsafeSlice, unsafeIndex
+) where
 
 import qualified Data.Vector.MVector as MVector
 import           Data.Vector.MVector ( MVector )
 
 import qualified Data.Vector.MVector as MVector
 import           Data.Vector.MVector ( MVector )
@@ -20,17 +63,44 @@ import Prelude hiding ( length,
                         filter, takeWhile, dropWhile,
                         foldl, foldl1, foldr, foldr1 )
 
                         filter, takeWhile, dropWhile,
                         foldl, foldl1, foldr, foldr1 )
 
+-- | Class of immutable vectors. Just like with 'MVector', the type of the
+-- elements can be restricted by using GADTs.
+--
 class IVector v a where
 class IVector v a where
+  -- | Construct a pure vector from a monadic initialiser.
   create       :: (forall mv m. MVector mv m a => m (mv m a)) -> v a
 
   create       :: (forall mv m. MVector mv m a => m (mv m a)) -> v a
 
+  -- | Length of the vector
   length       :: v a -> Int
   length       :: v a -> Int
+
+  -- | Yield a part of the vector without copying it. No range checks!
   unsafeSlice  :: v a -> Int -> Int -> v a
 
   unsafeSlice  :: v a -> Int -> Int -> v a
 
+  -- | Apply the given function to the element at the given position. This
+  -- interface prevents us from being too lazy. Suppose we had
+  --
+  -- > unsafeIndex' :: v a -> Int -> a
+  --
+  -- instead. Now, if we wanted to copy a vector, we'd do something like
+  --
+  -- > copy mv v ... = ... unsafeWrite mv i (unsafeIndex' v i) ...
+  --
+  -- For lazy vectors, the indexing would not be evaluated which means that we
+  -- would retain a reference to the original vector in each element we write.
+  -- This would be bad!
+  --
+  -- With 'unsafeIndex', we can do
+  --
+  -- > copy mv v ... = ... unsafeIndex v i (unsafeWrite mv i) ...
+  --
+  -- which does not have this problem.
+  --
   unsafeIndex  :: v a -> Int -> (a -> b) -> b
 
   unsafeIndex  :: v a -> Int -> (a -> b) -> b
 
+-- | Convert a vector to a 'Stream'
 stream :: IVector v a => v a -> Stream a
 {-# INLINE_STREAM stream #-}
 stream :: IVector v a => v a -> Stream a
 {-# INLINE_STREAM stream #-}
-stream !v = Stream.unfold get 0 `Stream.sized` Exact n
+stream v = v `seq` (Stream.unfold get 0 `Stream.sized` Exact n)
   where
     n = length v
 
   where
     n = length v
 
@@ -38,6 +108,7 @@ stream !v = Stream.unfold get 0 `Stream.sized` Exact n
     get i | i < n     = unsafeIndex v i $ \x -> Just (x, i+1)
           | otherwise = Nothing
 
     get i | i < n     = unsafeIndex v i $ \x -> Just (x, i+1)
           | otherwise = Nothing
 
+-- | Create a vector from a 'Stream'
 unstream :: IVector v a => Stream a -> v a
 {-# INLINE_STREAM unstream #-}
 unstream s = create (MVector.unstream s)
 unstream :: IVector v a => Stream a -> v a
 {-# INLINE_STREAM unstream #-}
 unstream s = create (MVector.unstream s)
@@ -52,27 +123,33 @@ unstream s = create (MVector.unstream s)
 -- Construction
 -- ------------
 
 -- Construction
 -- ------------
 
+-- | Empty vector
 empty :: IVector v a => v a
 {-# INLINE empty #-}
 empty = unstream Stream.empty
 
 empty :: IVector v a => v a
 {-# INLINE empty #-}
 empty = unstream Stream.empty
 
+-- | Vector with exaclty one element
 singleton :: IVector v a => a -> v a
 {-# INLINE singleton #-}
 singleton x = unstream (Stream.singleton x)
 
 singleton :: IVector v a => a -> v a
 {-# INLINE singleton #-}
 singleton x = unstream (Stream.singleton x)
 
+-- | Vector of the given length with the given value in each position
 replicate :: IVector v a => Int -> a -> v a
 {-# INLINE replicate #-}
 replicate n = unstream . Stream.replicate n
 
 replicate :: IVector v a => Int -> a -> v a
 {-# INLINE replicate #-}
 replicate n = unstream . Stream.replicate n
 
+-- | Prepend an element
 cons :: IVector v a => a -> v a -> v a
 {-# INLINE cons #-}
 cons x = unstream . Stream.cons x . stream
 
 cons :: IVector v a => a -> v a -> v a
 {-# INLINE cons #-}
 cons x = unstream . Stream.cons x . stream
 
+-- | Append an element
 snoc :: IVector v a => v a -> a -> v a
 {-# INLINE snoc #-}
 snoc v = unstream . Stream.snoc (stream v)
 
 infixr 5 ++
 snoc :: IVector v a => v a -> a -> v a
 {-# INLINE snoc #-}
 snoc v = unstream . Stream.snoc (stream v)
 
 infixr 5 ++
+-- | Concatenate two vectors
 (++) :: IVector v a => v a -> v a -> v a
 {-# INLINE (++) #-}
 v ++ w = unstream (stream v Stream.++ stream w)
 (++) :: IVector v a => v a -> v a -> v a
 {-# INLINE (++) #-}
 v ++ w = unstream (stream v Stream.++ stream w)
@@ -80,10 +157,12 @@ v ++ w = unstream (stream v Stream.++ stream w)
 -- Subarrays
 -- ---------
 
 -- Subarrays
 -- ---------
 
+-- | Copy the first @n@ elements to a new vector.
 take :: IVector v a => Int -> v a -> v a
 {-# INLINE take #-}
 take n = unstream . Stream.take n . stream
 
 take :: IVector v a => Int -> v a -> v a
 {-# INLINE take #-}
 take n = unstream . Stream.take n . stream
 
+-- | Copy all but the first @n@ elements to a new vectors.
 drop :: IVector v a => Int -> v a -> v a
 {-# INLINE drop #-}
 drop n = unstream . Stream.drop n . stream
 drop :: IVector v a => Int -> v a -> v a
 {-# INLINE drop #-}
 drop n = unstream . Stream.drop n . stream
@@ -91,10 +170,12 @@ drop n = unstream . Stream.drop n . stream
 -- Mapping/zipping
 -- ---------------
 
 -- Mapping/zipping
 -- ---------------
 
+-- | Map a function over a vector
 map :: (IVector v a, IVector v b) => (a -> b) -> v a -> v b
 {-# INLINE map #-}
 map f = unstream . Stream.map f . stream
 
 map :: (IVector v a, IVector v b) => (a -> b) -> v a -> v b
 {-# INLINE map #-}
 map f = unstream . Stream.map f . stream
 
+-- | Zip two vectors with the given function.
 zipWith :: (IVector v a, IVector v b, IVector v c) => (a -> b -> c) -> v a -> v b -> v c
 {-# INLINE zipWith #-}
 zipWith f xs ys = unstream (Stream.zipWith f (stream xs) (stream ys))
 zipWith :: (IVector v a, IVector v b, IVector v c) => (a -> b -> c) -> v a -> v b -> v c
 {-# INLINE zipWith #-}
 zipWith f xs ys = unstream (Stream.zipWith f (stream xs) (stream ys))
@@ -102,14 +183,19 @@ zipWith f xs ys = unstream (Stream.zipWith f (stream xs) (stream ys))
 -- Filtering
 -- ---------
 
 -- Filtering
 -- ---------
 
+-- | Drop elements which do not satisfy the predicate
 filter :: IVector v a => (a -> Bool) -> v a -> v a
 {-# INLINE filter #-}
 filter f = unstream . Stream.filter f . stream
 
 filter :: IVector v a => (a -> Bool) -> v a -> v a
 {-# INLINE filter #-}
 filter f = unstream . Stream.filter f . stream
 
+-- | Copy the longest prefix of elements satisfying the predicate to a new
+-- vector
 takeWhile :: IVector v a => (a -> Bool) -> v a -> v a
 {-# INLINE takeWhile #-}
 takeWhile f = unstream . Stream.takeWhile f . stream
 
 takeWhile :: IVector v a => (a -> Bool) -> v a -> v a
 {-# INLINE takeWhile #-}
 takeWhile f = unstream . Stream.takeWhile f . stream
 
+-- | Drop the longest prefix of elements that satisfy the predicate and copy
+-- the rest to a new vector.
 dropWhile :: IVector v a => (a -> Bool) -> v a -> v a
 {-# INLINE dropWhile #-}
 dropWhile f = unstream . Stream.dropWhile f . stream
 dropWhile :: IVector v a => (a -> Bool) -> v a -> v a
 {-# INLINE dropWhile #-}
 dropWhile f = unstream . Stream.dropWhile f . stream
@@ -117,34 +203,42 @@ dropWhile f = unstream . Stream.dropWhile f . stream
 -- Folding
 -- -------
 
 -- Folding
 -- -------
 
+-- | Left fold
 foldl :: IVector v b => (a -> b -> a) -> a -> v b -> a
 {-# INLINE foldl #-}
 foldl f z = Stream.foldl f z . stream
 
 foldl :: IVector v b => (a -> b -> a) -> a -> v b -> a
 {-# INLINE foldl #-}
 foldl f z = Stream.foldl f z . stream
 
+-- | Lefgt fold on non-empty vectors
 foldl1 :: IVector v a => (a -> a -> a) -> v a -> a
 {-# INLINE foldl1 #-}
 foldl1 f = Stream.foldl1 f . stream
 
 foldl1 :: IVector v a => (a -> a -> a) -> v a -> a
 {-# INLINE foldl1 #-}
 foldl1 f = Stream.foldl1 f . stream
 
+-- | Left fold with strict accumulator
 foldl' :: IVector v b => (a -> b -> a) -> a -> v b -> a
 {-# INLINE foldl' #-}
 foldl' f z = Stream.foldl' f z . stream
 
 foldl' :: IVector v b => (a -> b -> a) -> a -> v b -> a
 {-# INLINE foldl' #-}
 foldl' f z = Stream.foldl' f z . stream
 
+-- | Left fold on non-empty vectors with strict accumulator
 foldl1' :: IVector v a => (a -> a -> a) -> v a -> a
 {-# INLINE foldl1' #-}
 foldl1' f = Stream.foldl1' f . stream
 
 foldl1' :: IVector v a => (a -> a -> a) -> v a -> a
 {-# INLINE foldl1' #-}
 foldl1' f = Stream.foldl1' f . stream
 
+-- | Right fold
 foldr :: IVector v a => (a -> b -> b) -> b -> v a -> b
 {-# INLINE foldr #-}
 foldr f z = Stream.foldr f z . stream
 
 foldr :: IVector v a => (a -> b -> b) -> b -> v a -> b
 {-# INLINE foldr #-}
 foldr f z = Stream.foldr f z . stream
 
+-- | Right fold on non-empty vectors
 foldr1 :: IVector v a => (a -> a -> a) -> v a -> a
 {-# INLINE foldr1 #-}
 foldr1 f = Stream.foldr1 f . stream
 
 foldr1 :: IVector v a => (a -> a -> a) -> v a -> a
 {-# INLINE foldr1 #-}
 foldr1 f = Stream.foldr1 f . stream
 
+-- | Convert a vector to a list
 toList :: IVector v a => v a -> [a]
 {-# INLINE toList #-}
 toList = Stream.toList . stream
 
 toList :: IVector v a => v a -> [a]
 {-# INLINE toList #-}
 toList = Stream.toList . stream
 
+-- | Convert a list to a vector
 fromList :: IVector v a => [a] -> v a
 {-# INLINE fromList #-}
 fromList = unstream . Stream.fromList
 fromList :: IVector v a => [a] -> v a
 {-# INLINE fromList #-}
 fromList = unstream . Stream.fromList
index 32f358f..d519e61 100644 (file)
@@ -1,4 +1,16 @@
 {-# LANGUAGE MultiParamTypeClasses #-}
 {-# LANGUAGE MultiParamTypeClasses #-}
+-- |
+-- Module      : Data.Vector.MVector
+-- Copyright   : (c) Roman Leshchinskiy 2008
+-- License     : BSD-style
+--
+-- Maintainer  : rl@cse.unsw.edu.au
+-- Stability   : experimental
+-- Portability : non-portable
+-- 
+-- Generic interface to mutable vectors
+--
+
 module Data.Vector.MVector (
   MVector(..),
 
 module Data.Vector.MVector (
   MVector(..),
 
@@ -21,20 +33,55 @@ import Prelude hiding ( length, read )
 gROWTH_FACTOR :: Double
 gROWTH_FACTOR = 1.5
 
 gROWTH_FACTOR :: Double
 gROWTH_FACTOR = 1.5
 
+-- | Class of mutable vectors. The type @m@ is the monad in which the mutable
+-- vector can be transformed and @a@ is the type of elements. A vector does
+-- not necessarily have to be generic in either of them (indeed, it would be
+-- unusual for a vector to be generic in the monad). Use GADTs if this is the
+-- case. For instance, regular boxed vectors are defined as
+--
+-- > data Vector m a where
+-- >   Vector :: !Int -> !Int -> MutableArray# s a -> Vector (ST s) a
+--
+-- This is a bit clumsy but I haven't been able to find a better solution. In
+-- particular, using a type function for the monad triggers
+-- <http://hackage.haskell.org/trac/ghc/ticket/2440> and is probably less
+-- portable.
+--
 class Monad m => MVector v m a where
 class Monad m => MVector v m a where
+  -- | Length of the mutable vector
   length           :: v m a -> Int
   length           :: v m a -> Int
-  unsafeSlice      :: v m a -> Int -> Int -> v m a
 
 
+  -- | Yield a part of the mutable vector without copying it. No range checks!
+  unsafeSlice      :: v m a -> Int  -- ^ starting index
+                            -> Int  -- ^ length of the slice
+                            -> v m a
+
+  -- | Create a mutable vector of the given length. Length is not checked!
   unsafeNew        :: Int -> m (v m a)
   unsafeNew        :: Int -> m (v m a)
+
+  -- | Create a mutable vector of the given length and fill it with an
+  -- initial value. Length is not checked!
   unsafeNewWith    :: Int -> a -> m (v m a)
 
   unsafeNewWith    :: Int -> a -> m (v m a)
 
+  -- | Yield the element at the given position. Index is not checked!
   unsafeRead       :: v m a -> Int -> m a
   unsafeRead       :: v m a -> Int -> m a
+
+  -- | Replace the element at the given position. Index is not checked!
   unsafeWrite      :: v m a -> Int -> a -> m ()
 
   unsafeWrite      :: v m a -> Int -> a -> m ()
 
+  -- | Write the value at each position.
   set              :: v m a -> a -> m ()
   set              :: v m a -> a -> m ()
-  unsafeCopy       :: v m a -> v m a -> m ()
+
+  -- | Copy a vector. The two vectors may not overlap. This is not checked!
+  unsafeCopy       :: v m a   -- ^ target
+                   -> v m a   -- ^ source
+                   -> m ()
+
+  -- | Grow a vector by the given number of elements. The length is not
+  -- checked!
   unsafeGrow       :: v m a -> Int -> m (v m a)
 
   unsafeGrow       :: v m a -> Int -> m (v m a)
 
+  -- Check whether two vectors overlap.
   overlaps         :: v m a -> v m a -> Bool
 
   {-# INLINE unsafeNewWith #-}
   overlaps         :: v m a -> v m a -> Bool
 
   {-# INLINE unsafeNewWith #-}
@@ -72,42 +119,59 @@ class Monad m => MVector v m a where
     where
       n = length v
 
     where
       n = length v
 
+-- | Test whether the index is valid for the vector
 inBounds :: MVector v m a => v m a -> Int -> Bool
 {-# INLINE inBounds #-}
 inBounds v i = i >= 0 && i < length v
 
 inBounds :: MVector v m a => v m a -> Int -> Bool
 {-# INLINE inBounds #-}
 inBounds v i = i >= 0 && i < length v
 
+-- | Yield a part of the mutable vector without copying it. Safer version of
+-- 'unsafeSlice'.
 slice :: MVector v m a => v m a -> Int -> Int -> v m a
 {-# INLINE slice #-}
 slice v i n = assert (i >=0 && n >= 0 && i+n <= length v)
             $ unsafeSlice v i n
 
 slice :: MVector v m a => v m a -> Int -> Int -> v m a
 {-# INLINE slice #-}
 slice v i n = assert (i >=0 && n >= 0 && i+n <= length v)
             $ unsafeSlice v i n
 
+-- | Create a mutable vector of the given length. Safer version of
+-- 'unsafeNew'.
 new :: MVector v m a => Int -> m (v m a)
 {-# INLINE new #-}
 new n = assert (n >= 0) $ unsafeNew n
 
 new :: MVector v m a => Int -> m (v m a)
 {-# INLINE new #-}
 new n = assert (n >= 0) $ unsafeNew n
 
+-- | Create a mutable vector of the given length and fill it with an
+-- initial value. Safer version of 'unsafeNewWith'.
 newWith :: MVector v m a => Int -> a -> m (v m a)
 {-# INLINE newWith #-}
 newWith n x = assert (n >= 0) $ unsafeNewWith n x
 
 newWith :: MVector v m a => Int -> a -> m (v m a)
 {-# INLINE newWith #-}
 newWith n x = assert (n >= 0) $ unsafeNewWith n x
 
+-- | Yield the element at the given position. Safer version of 'unsafeRead'.
 read :: MVector v m a => v m a -> Int -> m a
 {-# INLINE read #-}
 read v i = assert (inBounds v i) $ unsafeRead v i
 
 read :: MVector v m a => v m a -> Int -> m a
 {-# INLINE read #-}
 read v i = assert (inBounds v i) $ unsafeRead v i
 
+-- | Replace the element at the given position. Safer version of
+-- 'unsafeWrite'.
 write :: MVector v m a => v m a -> Int -> a -> m ()
 {-# INLINE write #-}
 write v i x = assert (inBounds v i) $ unsafeWrite v i x
 
 write :: MVector v m a => v m a -> Int -> a -> m ()
 {-# INLINE write #-}
 write v i x = assert (inBounds v i) $ unsafeWrite v i x
 
+-- | Copy a vector. The two vectors may not overlap. Safer version of
+-- 'unsafeCopy'.
 copy :: MVector v m a => v m a -> v m a -> m ()
 {-# INLINE copy #-}
 copy dst src = assert (not (dst `overlaps` src) && length dst == length src)
              $ unsafeCopy dst src
 
 copy :: MVector v m a => v m a -> v m a -> m ()
 {-# INLINE copy #-}
 copy dst src = assert (not (dst `overlaps` src) && length dst == length src)
              $ unsafeCopy dst src
 
+-- | Grow a vector by the given number of elements. Safer version of
+-- 'unsafeGrow'.
 grow :: MVector v m a => v m a -> Int -> m (v m a)
 {-# INLINE grow #-}
 grow v by = assert (by >= 0)
           $ unsafeGrow v by
 
 
 grow :: MVector v m a => v m a -> Int -> m (v m a)
 {-# INLINE grow #-}
 grow v by = assert (by >= 0)
           $ unsafeGrow v by
 
 
+-- | Create a new mutable vector and fill it with elements from the 'Stream'.
+-- The vector will grow logarithmically if the 'Size' hint of the 'Stream' is
+-- inexact.
 unstream :: MVector v m a => Stream a -> m (v m a)
 {-# INLINE unstream #-}
 unstream s = case upperBound (Stream.size s) of
 unstream :: MVector v m a => Stream a -> m (v m a)
 {-# INLINE unstream #-}
 unstream s = case upperBound (Stream.size s) of
index 2dc2437..6980de7 100644 (file)
@@ -1,18 +1,54 @@
-{-# LANGUAGE ExistentialQuantification, BangPatterns, CPP #-}
+{-# LANGUAGE ExistentialQuantification #-}
+
+-- |
+-- Module      : Data.Vector.Stream.Size
+-- Copyright   : (c) Roman Leshchinskiy 2008
+-- License     : BSD-style
+--
+-- Maintainer  : rl@cse.unsw.edu.au
+-- Stability   : experimental
+-- Portability : non-portable
+-- 
+-- Fusible streams
+--
 
 #include "phases.h"
 
 module Data.Vector.Stream (
 
 #include "phases.h"
 
 module Data.Vector.Stream (
+  -- * Types
   Step(..), Stream(..),
 
   Step(..), Stream(..),
 
-  size, sized, unfold, toList, fromList,
+  -- * Size hints
+  size, sized,
+
+  -- * Length information
   length, null,
   length, null,
+
+  -- * Construction
   empty, singleton, cons, snoc, replicate, (++),
   empty, singleton, cons, snoc, replicate, (++),
+
+  -- * Accessing individual elements
   head, last, (!!),
   head, last, (!!),
+
+  -- * Substreams
   init, tail, take, drop,
   init, tail, take, drop,
+
+  -- * Mapping and zipping
   map, zipWith,
   map, zipWith,
+
+  -- * Filtering
   filter, takeWhile, dropWhile,
   filter, takeWhile, dropWhile,
+
+  -- * Folding
   foldl, foldl1, foldl', foldl1', foldr, foldr1,
   foldl, foldl1, foldl', foldl1', foldr, foldr1,
+
+  -- * Unfolding
+  unfold,
+
+  -- * Conversion to/from lists
+  toList, fromList,
+
+  -- * Monadic combinators
   mapM_, foldM
 ) where
 
   mapM_, foldM
 ) where
 
@@ -31,16 +67,20 @@ data Step s a = Yield a s
               | Skip    s
               | Done
 
               | Skip    s
               | Done
 
+-- | The type of fusible streams
 data Stream a = forall s. Stream (s -> Step s a) s Size
 
 data Stream a = forall s. Stream (s -> Step s a) s Size
 
+-- | 'Size' hint of a 'Stream'
 size :: Stream a -> Size
 {-# INLINE size #-}
 size (Stream _ _ sz) = sz
 
 size :: Stream a -> Size
 {-# INLINE size #-}
 size (Stream _ _ sz) = sz
 
+-- | Attach a 'Size' hint to a 'Stream'
 sized :: Stream a -> Size -> Stream a
 {-# INLINE_STREAM sized #-}
 sized (Stream step s _) sz = Stream step s sz
 
 sized :: Stream a -> Size -> Stream a
 {-# INLINE_STREAM sized #-}
 sized (Stream step s _) sz = Stream step s sz
 
+-- | Unfold
 unfold :: (s -> Maybe (a, s)) -> s -> Stream a
 {-# INLINE_STREAM unfold #-}
 unfold f s = Stream step s Unknown
 unfold :: (s -> Maybe (a, s)) -> s -> Stream a
 {-# INLINE_STREAM unfold #-}
 unfold f s = Stream step s Unknown
@@ -50,10 +90,12 @@ unfold f s = Stream step s Unknown
                Just (x, s') -> Yield x s'
                Nothing      -> Done
 
                Just (x, s') -> Yield x s'
                Nothing      -> Done
 
+-- | Convert a 'Stream' to a list
 toList :: Stream a -> [a]
 {-# INLINE toList #-}
 toList s = foldr (:) [] s
 
 toList :: Stream a -> [a]
 {-# INLINE toList #-}
 toList s = foldr (:) [] s
 
+-- | Create a 'Stream' from a list
 fromList :: [a] -> Stream a
 {-# INLINE_STREAM fromList #-}
 fromList xs = Stream step xs Unknown
 fromList :: [a] -> Stream a
 {-# INLINE_STREAM fromList #-}
 fromList xs = Stream step xs Unknown
@@ -64,10 +106,12 @@ fromList xs = Stream step xs Unknown
 -- Length
 -- ------
 
 -- Length
 -- ------
 
+-- | Length of a 'Stream'
 length :: Stream a -> Int
 {-# INLINE_STREAM length #-}
 length s = foldl' (\n _ -> n+1) 0 s
 
 length :: Stream a -> Int
 {-# INLINE_STREAM length #-}
 length s = foldl' (\n _ -> n+1) 0 s
 
+-- | Check if a 'Stream' is empty
 null :: Stream a -> Bool
 {-# INLINE_STREAM null #-}
 null s = foldr (\_ _ -> False) True s
 null :: Stream a -> Bool
 {-# INLINE_STREAM null #-}
 null s = foldr (\_ _ -> False) True s
@@ -75,10 +119,12 @@ null s = foldr (\_ _ -> False) True s
 -- Construction
 -- ------------
 
 -- Construction
 -- ------------
 
+-- | Empty 'Stream'
 empty :: Stream a
 {-# INLINE_STREAM empty #-}
 empty = Stream (const Done) () (Exact 0)
 
 empty :: Stream a
 {-# INLINE_STREAM empty #-}
 empty = Stream (const Done) () (Exact 0)
 
+-- | Singleton 'Stream'
 singleton :: a -> Stream a
 {-# INLINE_STREAM singleton #-}
 singleton x = Stream step True (Exact 1)
 singleton :: a -> Stream a
 {-# INLINE_STREAM singleton #-}
 singleton x = Stream step True (Exact 1)
@@ -87,6 +133,7 @@ singleton x = Stream step True (Exact 1)
     step True  = Yield x False
     step False = Done
 
     step True  = Yield x False
     step False = Done
 
+-- | Replicate a value to a given length
 replicate :: Int -> a -> Stream a
 {-# INLINE_STREAM replicate #-}
 replicate n x = Stream step n (Exact (max n 0))
 replicate :: Int -> a -> Stream a
 {-# INLINE_STREAM replicate #-}
 replicate n x = Stream step n (Exact (max n 0))
@@ -95,15 +142,18 @@ replicate n x = Stream step n (Exact (max n 0))
     step i | i > 0     = Yield x (i-1)
            | otherwise = Done
 
     step i | i > 0     = Yield x (i-1)
            | otherwise = Done
 
+-- | Prepend an element
 cons :: a -> Stream a -> Stream a
 {-# INLINE cons #-}
 cons x s = singleton x ++ s
 
 cons :: a -> Stream a -> Stream a
 {-# INLINE cons #-}
 cons x s = singleton x ++ s
 
+-- | Append an element
 snoc :: Stream a -> a -> Stream a
 {-# INLINE snoc #-}
 snoc s x = s ++ singleton x
 
 infixr 5 ++
 snoc :: Stream a -> a -> Stream a
 {-# INLINE snoc #-}
 snoc s x = s ++ singleton x
 
 infixr 5 ++
+-- | Concatenate two 'Stream's
 (++) :: Stream a -> Stream a -> Stream a
 {-# INLINE_STREAM (++) #-}
 Stream stepa sa na ++ Stream stepb sb nb = Stream step (Left sa) (na + nb)
 (++) :: Stream a -> Stream a -> Stream a
 {-# INLINE_STREAM (++) #-}
 Stream stepa sa na ++ Stream stepb sb nb = Stream step (Left sa) (na + nb)
@@ -120,6 +170,7 @@ Stream stepa sa na ++ Stream stepb sb nb = Stream step (Left sa) (na + nb)
 -- Accessing elements
 -- ------------------
 
 -- Accessing elements
 -- ------------------
 
+-- | First element of the 'Stream' or error if empty
 head :: Stream a -> a
 {-# INLINE_STREAM head #-}
 head (Stream step s _) = head_loop s
 head :: Stream a -> a
 {-# INLINE_STREAM head #-}
 head (Stream step s _) = head_loop s
@@ -129,6 +180,7 @@ head (Stream step s _) = head_loop s
                     Skip    s' -> head_loop s'
                     Done       -> error "Data.Vector.Stream.head: empty stream"
 
                     Skip    s' -> head_loop s'
                     Done       -> error "Data.Vector.Stream.head: empty stream"
 
+-- | Last element of the 'Stream' or error if empty
 last :: Stream a -> a
 {-# INLINE_STREAM last #-}
 last (Stream step s _) = last_loop0 s
 last :: Stream a -> a
 {-# INLINE_STREAM last #-}
 last (Stream step s _) = last_loop0 s
@@ -143,6 +195,7 @@ last (Stream step s _) = last_loop0 s
                        Skip    s' -> last_loop1 x s'
                        Done       -> x
 
                        Skip    s' -> last_loop1 x s'
                        Done       -> x
 
+-- | Element at the given position
 (!!) :: Stream a -> Int -> a
 {-# INLINE (!!) #-}
 s !! i = head (drop i s)
 (!!) :: Stream a -> Int -> a
 {-# INLINE (!!) #-}
 s !! i = head (drop i s)
@@ -150,6 +203,7 @@ s !! i = head (drop i s)
 -- Substreams
 -- ----------
 
 -- Substreams
 -- ----------
 
+-- | All but the last element
 init :: Stream a -> Stream a
 {-# INLINE_STREAM init #-}
 init (Stream step s sz) = Stream step' (Nothing, s) (sz - 1)
 init :: Stream a -> Stream a
 {-# INLINE_STREAM init #-}
 init (Stream step s sz) = Stream step' (Nothing, s) (sz - 1)
@@ -165,6 +219,7 @@ init (Stream step s sz) = Stream step' (Nothing, s) (sz - 1)
                            Skip    s' -> Skip    (Just x, s')
                            Done       -> Done
 
                            Skip    s' -> Skip    (Just x, s')
                            Done       -> Done
 
+-- | All but the first element
 tail :: Stream a -> Stream a
 {-# INLINE_STREAM tail #-}
 tail (Stream step s sz) = Stream step' (Left s) (sz - 1)
 tail :: Stream a -> Stream a
 {-# INLINE_STREAM tail #-}
 tail (Stream step s sz) = Stream step' (Left s) (sz - 1)
@@ -180,6 +235,7 @@ tail (Stream step s sz) = Stream step' (Left s) (sz - 1)
                         Skip    s' -> Skip    (Right s')
                         Done       -> Done
 
                         Skip    s' -> Skip    (Right s')
                         Done       -> Done
 
+-- | The first @n@ elements
 take :: Int -> Stream a -> Stream a
 {-# INLINE_STREAM take #-}
 take n (Stream step s sz) = Stream step' (s, 0) (smaller (Exact n) sz)
 take :: Int -> Stream a -> Stream a
 {-# INLINE_STREAM take #-}
 take n (Stream step s sz) = Stream step' (s, 0) (smaller (Exact n) sz)
@@ -193,6 +249,7 @@ take n (Stream step s sz) = Stream step' (s, 0) (smaller (Exact n) sz)
 
 data Drop s = Drop_Drop s Int | Drop_Keep s
 
 
 data Drop s = Drop_Drop s Int | Drop_Keep s
 
+-- | All but the first @n@ elements
 drop :: Int -> Stream a -> Stream a
 {-# INLINE_STREAM drop #-}
 drop n (Stream step s sz) = Stream step' (Drop_Drop s 0) (sz - Exact n)
 drop :: Int -> Stream a -> Stream a
 {-# INLINE_STREAM drop #-}
 drop n (Stream step s sz) = Stream step' (Drop_Drop s 0) (sz - Exact n)
@@ -217,6 +274,7 @@ instance Functor Stream where
   {-# INLINE_STREAM fmap #-}
   fmap = map
 
   {-# INLINE_STREAM fmap #-}
   fmap = map
 
+-- | Map a function over a 'Stream'
 map :: (a -> b) -> Stream a -> Stream b
 {-# INLINE_STREAM map #-}
 map f (Stream step s n) = Stream step' s n
 map :: (a -> b) -> Stream a -> Stream b
 {-# INLINE_STREAM map #-}
 map f (Stream step s n) = Stream step' s n
@@ -227,6 +285,7 @@ map f (Stream step s n) = Stream step' s n
                 Skip    s' -> Skip        s'
                 Done       -> Done
 
                 Skip    s' -> Skip        s'
                 Done       -> Done
 
+-- | Zip two 'Stream's with the given function
 zipWith :: (a -> b -> c) -> Stream a -> Stream b -> Stream c
 {-# INLINE_STREAM zipWith #-}
 zipWith f (Stream stepa sa na) (Stream stepb sb nb)
 zipWith :: (a -> b -> c) -> Stream a -> Stream b -> Stream c
 {-# INLINE_STREAM zipWith #-}
 zipWith f (Stream stepa sa na) (Stream stepb sb nb)
@@ -246,6 +305,7 @@ zipWith f (Stream stepa sa na) (Stream stepb sb nb)
 -- Filtering
 -- ---------
 
 -- Filtering
 -- ---------
 
+-- | Drop elements which do not satisfy the predicate
 filter :: (a -> Bool) -> Stream a -> Stream a
 {-# INLINE_STREAM filter #-}
 filter f (Stream step s n) = Stream step' s (toMax n)
 filter :: (a -> Bool) -> Stream a -> Stream a
 {-# INLINE_STREAM filter #-}
 filter f (Stream step s n) = Stream step' s (toMax n)
@@ -257,6 +317,7 @@ filter f (Stream step s n) = Stream step' s (toMax n)
                 Skip    s'             -> Skip    s'
                 Done                   -> Done
 
                 Skip    s'             -> Skip    s'
                 Done                   -> Done
 
+-- | Longest prefix of elements that satisfy the predicate
 takeWhile :: (a -> Bool) -> Stream a -> Stream a
 {-# INLINE_STREAM takeWhile #-}
 takeWhile f (Stream step s n) = Stream step' s (toMax n)
 takeWhile :: (a -> Bool) -> Stream a -> Stream a
 {-# INLINE_STREAM takeWhile #-}
 takeWhile f (Stream step s n) = Stream step' s (toMax n)
@@ -271,6 +332,7 @@ takeWhile f (Stream step s n) = Stream step' s (toMax n)
 
 data DropWhile s a = DropWhile_Drop s | DropWhile_Yield a s | DropWhile_Next s
 
 
 data DropWhile s a = DropWhile_Drop s | DropWhile_Yield a s | DropWhile_Next s
 
+-- | Drop the longest prefix of elements that satisfy the predicate
 dropWhile :: (a -> Bool) -> Stream a -> Stream a
 {-# INLINE_STREAM dropWhile #-}
 dropWhile f (Stream step s n) = Stream step' (DropWhile_Drop s) (toMax n)
 dropWhile :: (a -> Bool) -> Stream a -> Stream a
 {-# INLINE_STREAM dropWhile #-}
 dropWhile f (Stream step s n) = Stream step' (DropWhile_Drop s) (toMax n)
@@ -296,6 +358,7 @@ dropWhile f (Stream step s n) = Stream step' (DropWhile_Drop s) (toMax n)
 -- Folding
 -- -------
 
 -- Folding
 -- -------
 
+-- | Left fold
 foldl :: (a -> b -> a) -> a -> Stream b -> a
 {-# INLINE_STREAM foldl #-}
 foldl f z (Stream step s _) = foldl_go z s
 foldl :: (a -> b -> a) -> a -> Stream b -> a
 {-# INLINE_STREAM foldl #-}
 foldl f z (Stream step s _) = foldl_go z s
@@ -305,6 +368,7 @@ foldl f z (Stream step s _) = foldl_go z s
                      Skip    s' -> foldl_go z       s'
                      Done       -> z
 
                      Skip    s' -> foldl_go z       s'
                      Done       -> z
 
+-- | Left fold on non-empty 'Stream's
 foldl1 :: (a -> a -> a) -> Stream a -> a
 {-# INLINE_STREAM foldl1 #-}
 foldl1 f (Stream step s sz) = foldl1_loop s
 foldl1 :: (a -> a -> a) -> Stream a -> a
 {-# INLINE_STREAM foldl1 #-}
 foldl1 f (Stream step s sz) = foldl1_loop s
@@ -314,6 +378,7 @@ foldl1 f (Stream step s sz) = foldl1_loop s
                       Skip    s' -> foldl1_loop s'
                       Done       -> error "Data.Vector.Stream.foldl1: empty stream"
 
                       Skip    s' -> foldl1_loop s'
                       Done       -> error "Data.Vector.Stream.foldl1: empty stream"
 
+-- | Left fold with strict accumulator
 foldl' :: (a -> b -> a) -> a -> Stream b -> a
 {-# INLINE_STREAM foldl' #-}
 foldl' f z (Stream step s _) = foldl_go z s
 foldl' :: (a -> b -> a) -> a -> Stream b -> a
 {-# INLINE_STREAM foldl' #-}
 foldl' f z (Stream step s _) = foldl_go z s
@@ -324,6 +389,7 @@ foldl' f z (Stream step s _) = foldl_go z s
                      Skip    s' -> foldl_go z       s'
                      Done       -> z
 
                      Skip    s' -> foldl_go z       s'
                      Done       -> z
 
+-- | Left fold on non-empty 'Stream's with strict accumulator
 foldl1' :: (a -> a -> a) -> Stream a -> a
 {-# INLINE_STREAM foldl1' #-}
 foldl1' f (Stream step s sz) = foldl1'_loop s
 foldl1' :: (a -> a -> a) -> Stream a -> a
 {-# INLINE_STREAM foldl1' #-}
 foldl1' f (Stream step s sz) = foldl1'_loop s
@@ -333,7 +399,7 @@ foldl1' f (Stream step s sz) = foldl1'_loop s
                       Skip    s' -> foldl1'_loop s'
                       Done       -> error "Data.Vector.Stream.foldl1': empty stream"
 
                       Skip    s' -> foldl1'_loop s'
                       Done       -> error "Data.Vector.Stream.foldl1': empty stream"
 
-
+-- | Right fold
 foldr :: (a -> b -> b) -> b -> Stream a -> b
 {-# INLINE_STREAM foldr #-}
 foldr f z (Stream step s _) = foldr_go s
 foldr :: (a -> b -> b) -> b -> Stream a -> b
 {-# INLINE_STREAM foldr #-}
 foldr f z (Stream step s _) = foldr_go s
@@ -343,6 +409,7 @@ foldr f z (Stream step s _) = foldr_go s
                    Skip    s' -> foldr_go s'
                    Done       -> z
 
                    Skip    s' -> foldr_go s'
                    Done       -> z
 
+-- | Right fold on non-empty 'Stream's
 foldr1 :: (a -> a -> a) -> Stream a -> a
 {-# INLINE_STREAM foldr1 #-}
 foldr1 f (Stream step s sz) = foldr1_loop s
 foldr1 :: (a -> a -> a) -> Stream a -> a
 {-# INLINE_STREAM foldr1 #-}
 foldr1 f (Stream step s sz) = foldr1_loop s
@@ -352,6 +419,7 @@ foldr1 f (Stream step s sz) = foldr1_loop s
                       Skip    s' -> foldr1_loop s'
                       Done       -> error "Data.Vector.Stream.foldr1: empty stream"
 
                       Skip    s' -> foldr1_loop s'
                       Done       -> error "Data.Vector.Stream.foldr1: empty stream"
 
+-- | Apply a monadic action to each element of the stream
 mapM_ :: Monad m => (a -> m ()) -> Stream a -> m ()
 {-# INLINE_STREAM mapM_ #-}
 mapM_ m (Stream step s _) = mapM_go s
 mapM_ :: Monad m => (a -> m ()) -> Stream a -> m ()
 {-# INLINE_STREAM mapM_ #-}
 mapM_ m (Stream step s _) = mapM_go s
@@ -361,6 +429,7 @@ mapM_ m (Stream step s _) = mapM_go s
                    Skip    s' -> mapM_go s'
                    Done       -> return ()
 
                    Skip    s' -> mapM_go s'
                    Done       -> return ()
 
+-- | Monadic fold
 foldM :: Monad m => (a -> b -> m a) -> a -> Stream b -> m a
 {-# INLINE_STREAM foldM #-}
 foldM m z (Stream step s _) = foldM_go z s
 foldM :: Monad m => (a -> b -> m a) -> a -> Stream b -> m a
 {-# INLINE_STREAM foldM #-}
 foldM m z (Stream step s _) = foldM_go z s
index 6389256..254242d 100644 (file)
@@ -1,10 +1,23 @@
+-- |
+-- Module      : Data.Vector.Stream.Size
+-- Copyright   : (c) Roman Leshchinskiy 2008
+-- License     : BSD-style
+--
+-- Maintainer  : rl@cse.unsw.edu.au
+-- Stability   : experimental
+-- Portability : portable
+-- 
+-- Size hints
+--
+
 module Data.Vector.Stream.Size (
   Size(..), smaller, larger, toMax, upperBound
 ) where
 
 module Data.Vector.Stream.Size (
   Size(..), smaller, larger, toMax, upperBound
 ) where
 
-data Size = Exact Int
-          | Max   Int
-          | Unknown
+-- | Size hint
+data Size = Exact Int          -- ^ Exact size
+          | Max   Int          -- ^ Upper bound on the size
+          | Unknown            -- ^ Unknown size
         deriving( Eq, Show )
 
 instance Num Size where
         deriving( Eq, Show )
 
 instance Num Size where
@@ -29,7 +42,7 @@ instance Num Size where
 
   fromInteger n     = Exact (fromInteger n)
 
 
   fromInteger n     = Exact (fromInteger n)
 
-
+-- | Minimum of two size hints
 smaller :: Size -> Size -> Size
 smaller (Exact m) (Exact n) = Exact (m `min` n)
 smaller (Exact m) (Max   n) = Max   (m `min` n)
 smaller :: Size -> Size -> Size
 smaller (Exact m) (Exact n) = Exact (m `min` n)
 smaller (Exact m) (Max   n) = Max   (m `min` n)
@@ -41,6 +54,7 @@ smaller Unknown   (Exact n) = Max   n
 smaller Unknown   (Max   n) = Max   n
 smaller Unknown   Unknown   = Unknown
 
 smaller Unknown   (Max   n) = Max   n
 smaller Unknown   Unknown   = Unknown
 
+-- | Maximum of two size hints
 larger :: Size -> Size -> Size
 larger (Exact m) (Exact n)             = Exact (m `max` n)
 larger (Exact m) (Max   n) | m >= n    = Exact m
 larger :: Size -> Size -> Size
 larger (Exact m) (Exact n)             = Exact (m `max` n)
 larger (Exact m) (Max   n) | m >= n    = Exact m
@@ -50,15 +64,18 @@ larger (Max   m) (Exact n) | n >= m    = Exact n
 larger (Max   m) (Max   n)             = Max   (m `max` n)
 larger _         _                     = Unknown
 
 larger (Max   m) (Max   n)             = Max   (m `max` n)
 larger _         _                     = Unknown
 
+-- | Convert a size hint to an upper bound
 toMax :: Size -> Size
 toMax (Exact n) = Max n
 toMax (Max   n) = Max n
 toMax Unknown   = Unknown
 
 toMax :: Size -> Size
 toMax (Exact n) = Max n
 toMax (Max   n) = Max n
 toMax Unknown   = Unknown
 
+-- | Compute the minimum size from a size hint
 lowerBound :: Size -> Int
 lowerBound (Exact n) = n
 lowerBound _         = 0
 
 lowerBound :: Size -> Int
 lowerBound (Exact n) = n
 lowerBound _         = 0
 
+-- | Compute the maximum size from a size hint if possible
 upperBound :: Size -> Maybe Int
 upperBound (Exact n) = Just n
 upperBound (Max   n) = Just n
 upperBound :: Size -> Maybe Int
 upperBound (Exact n) = Just n
 upperBound (Max   n) = Just n
index 854b93a..ceae635 100644 (file)
@@ -1,5 +1,17 @@
 {-# LANGUAGE MagicHash, UnboxedTuples #-}
 
 {-# LANGUAGE MagicHash, UnboxedTuples #-}
 
+-- |
+-- Module      : Data.Vector.Unboxed.Unbox
+-- Copyright   : (c) Roman Leshchinskiy 2008
+-- License     : BSD-style
+--
+-- Maintainer  : rl@cse.unsw.edu.au
+-- Stability   : experimental
+-- Portability : non-portable
+-- 
+-- Primitives for manipulating unboxed arrays
+--
+
 module Data.Vector.Unboxed.Unbox (
   Unbox(..)
 ) where
 module Data.Vector.Unboxed.Unbox (
   Unbox(..)
 ) where
@@ -22,10 +34,20 @@ import Data.Array.Base (
     wORD_SCALE, fLOAT_SCALE, dOUBLE_SCALE
   )
 
     wORD_SCALE, fLOAT_SCALE, dOUBLE_SCALE
   )
 
+-- | Class of types which can be stored in unboxed arrays
 class Unbox a where
 class Unbox a where
-  size#  :: a -> Int# -> Int#
+  -- | Yield the size in bytes of a 'ByteArray#' which can store @n@ elements
+  size#  :: a     -- ^ Dummy type parameter, never evaluated
+         -> Int#  -- ^ Number of elements
+         -> Int#
+
+  -- | Indexing
   at#    :: ByteArray# -> Int# -> a
   at#    :: ByteArray# -> Int# -> a
+
+  -- | Yield the element at the given position
   read#  :: MutableByteArray# s -> Int# -> State# s -> (# State# s, a #)
   read#  :: MutableByteArray# s -> Int# -> State# s -> (# State# s, a #)
+
+  -- | Store the given element at the given position
   write# :: MutableByteArray# s -> Int# -> a -> State# s -> State# s
 
 instance Unbox Int where
   write# :: MutableByteArray# s -> Int# -> a -> State# s -> State# s
 
 instance Unbox Int where