Commits

Bryan O'Sullivan committed 2c14ebb

Implement and test strict and lazy zip

  • Participants
  • Parent commits fbd9352

Comments (0)

Files changed (4)

     , count
 
     -- * Zipping and unzipping
+    , zip
     , zipWith
 
     -- -* Ordered text
 -------------------------------------------------------------------------------
 -- * Zipping
 
+-- | /O(n)/ 'zip' takes two 'Text's and returns a list of
+-- corresponding pairs of bytes. If one input 'Text' is short,
+-- excess elements of the longer 'Text' are discarded. This is
+-- equivalent to a pair of 'unpack' operations.
+zip :: Text -> Text -> [(Char,Char)]
+zip a b = S.unstreamList $ S.zipWith (,) (stream a) (stream b)
+{-# INLINE [0] zip #-}
+
 -- | /O(n)/ 'zipWith' generalises 'zip' by zipping with the function
 -- given as the first argument, instead of a tupling function.
 zipWith :: (Char -> Char -> Char) -> Text -> Text -> Text

Data/Text/Fusion/Common.hs

 
 -- | zipWith generalises 'zip' by zipping with the function given as
 -- the first argument, instead of a tupling function.
-zipWith :: (Char -> Char -> Char) -> Stream Char -> Stream Char -> Stream Char
+zipWith :: (a -> a -> b) -> Stream a -> Stream a -> Stream b
 zipWith f (Stream next0 sa0 len1) (Stream next1 sb0 len2) = Stream next (sa0 :!: sb0 :!: Nothing) (min len1 len2)
     where
       {-# INLINE next #-}

Data/Text/Lazy.hs

     , count
 
     -- * Zipping and unzipping
+    , zip
     , zipWith
 
     -- -* Ordered text
     ) where
 
 import Prelude (Char, Bool(..), Int, Maybe(..), String,
-                Eq(..), Ord(..), (++),
-                Read(..), Show(..),
-                (&&), (+), (-), (.),
+                Eq(..), Ord(..), Read(..), Show(..),
+                (&&), (+), (-), (.), ($), (++),
                 flip, fromIntegral, not, otherwise)
 import qualified Prelude as P
 import Data.Int (Int64)
 count c t = S.count c (stream t)
 {-# INLINE count #-}
 
+-- | /O(n)/ 'zip' takes two 'Text's and returns a list of
+-- corresponding pairs of bytes. If one input 'Text' is short,
+-- excess elements of the longer 'Text' are discarded. This is
+-- equivalent to a pair of 'unpack' operations.
+zip :: Text -> Text -> [(Char,Char)]
+zip a b = S.unstreamList $ S.zipWith (,) (stream a) (stream b)
+{-# INLINE [0] zip #-}
+
 -- | /O(n)/ 'zipWith' generalises 'zip' by zipping with the function
 -- given as the first argument, instead of a tupling function.
 zipWith :: (Char -> Char -> Char) -> Text -> Text -> Text

tests/Properties.hs

 prop_TL_elemIndices c  = (fmap fromIntegral . L.elemIndices c) `eqP` TL.elemIndices c
 prop_T_count c         = (L.length . L.elemIndices c) `eqP` T.count c
 prop_TL_count c        = (fromIntegral . L.length . L.elemIndices c) `eqP` TL.count c
+prop_T_zip s           = L.zip s `eqP` T.zip (packS s)
+prop_TL_zip s          = L.zip s `eqP` TL.zip (packS s)
 prop_T_zipWith c s     = L.zipWith c s `eqP` (unpackS . T.zipWith c (packS s))
 prop_TL_zipWith c s    = L.zipWith c s `eqP` (unpackS . TL.zipWith c (packS s))
 
   ("prop_TL_elemIndices", mytest prop_TL_elemIndices),
   ("prop_T_count", mytest prop_T_count),
   ("prop_TL_count", mytest prop_TL_count),
+  ("prop_T_zip", mytest prop_T_zip),
+  ("prop_TL_zip", mytest prop_TL_zip),
   ("prop_T_zipWith", mytest prop_T_zipWith),
   ("prop_TL_zipWith", mytest prop_TL_zipWith),