on master help sign in
Implement count.
6f9ab7bBryan O'Sullivan
Data/Text.hs+18−11
@@ -133,7 +133,7 @@ module Data.Text
133 , findIndices
133 , findIndices
134 , elemIndex
134 , elemIndex
135 , elemIndices
135 , elemIndices
136− -- , count
136+ , count
137
137
138 -- * Zipping and unzipping
138 -- * Zipping and unzipping
139 , zipWith
139 , zipWith
@@ -561,9 +561,9 @@ take n t@(Text arr off len)
561 | n >= len = t
561 | n >= len = t
562 | otherwise = Text arr off (loop 0 0)
562 | otherwise = Text arr off (loop 0 0)
563 where
563 where
564− loop !i !count
564+ loop !i !cnt
565− | i >= len || count >= n = i
565+ | i >= len || cnt >= n = i
566− | otherwise = loop (i+d) (count+1)
566+ | otherwise = loop (i+d) (cnt+1)
567 where d = iter_ t i
567 where d = iter_ t i
568{-# INLINE [1] take #-}
568{-# INLINE [1] take #-}
569
569
@@ -583,9 +583,9 @@ drop n t@(Text arr off len)
583 | n >= len = empty
583 | n >= len = empty
584 | otherwise = loop 0 0
584 | otherwise = loop 0 0
585 where end = off + len
585 where end = off + len
586− loop !i !count
586+ loop !i !cnt
587− | i >= end || count >= n = Text arr (off+i) (len-i)
587+ | i >= end || cnt >= n = Text arr (off+i) (len-i)
588− | otherwise = loop (i+d) (count+1)
588+ | otherwise = loop (i+d) (cnt+1)
589 where d = iter_ t i
589 where d = iter_ t i
590{-# INLINE [1] drop #-}
590{-# INLINE [1] drop #-}
591
591
@@ -640,10 +640,10 @@ splitAt n t@(Text arr off len)
640 | n >= len = (t, empty)
640 | n >= len = (t, empty)
641 | otherwise = (Text arr off k, Text arr (off+k) (len-k))
641 | otherwise = (Text arr off k, Text arr (off+k) (len-k))
642 where k = loop 0 0
642 where k = loop 0 0
643− loop !i !count
643+ loop !i !cnt
644− | i >= len || count >= n = i
644+ | i >= len || cnt >= n = i
645− | otherwise = loop (i+d) (count+1)
645+ | otherwise = loop (i+d) (cnt+1)
646− where d = iter_ t i
646+ where d = iter_ t i
647{-# INLINE splitAt #-}
647{-# INLINE splitAt #-}
648
648
649-- | /O(n)/ 'span', applied to a predicate @p@ and text @t@, returns a
649-- | /O(n)/ 'span', applied to a predicate @p@ and text @t@, returns a
@@ -852,6 +852,13 @@ elemIndices :: Char -> Text -> [Int]
852elemIndices c t = S.elemIndices c (stream t)
852elemIndices c t = S.elemIndices c (stream t)
853{-# INLINE elemIndices #-}
853{-# INLINE elemIndices #-}
854
854
855+-- | /O(n)/ The 'count' function returns the number of times the query
856+-- element appears in the given 'Text'. This function is subject to
857+-- fusion.
858+count :: Char -> Text -> Int
859+count c t = S.count c (stream t)
860+{-# INLINE count #-}
861+
855-------------------------------------------------------------------------------
862-------------------------------------------------------------------------------
856-- * Zipping
863-- * Zipping
857
864
Data/Text/Fusion.hs+13
@@ -94,6 +94,7 @@ module Data.Text.Fusion
94 , findIndexOrEnd
94 , findIndexOrEnd
95 , elemIndex
95 , elemIndex
96 , elemIndices
96 , elemIndices
97+ , count
97
98
98 -- * Zipping and unzipping
99 -- * Zipping and unzipping
99 , zipWith
100 , zipWith
@@ -838,6 +839,18 @@ elemIndices a (Stream next s0 _len) = loop 0 s0
838 | otherwise -> loop (i+1) s'
839 | otherwise -> loop (i+1) s'
839{-# INLINE [0] elemIndices #-}
840{-# INLINE [0] elemIndices #-}
840
841
842+-- | /O(n)/ The 'count' function returns the number of times the query
843+-- element appears in the given stream.
844+count :: Char -> Stream Char -> Int
845+count a (Stream next s0 _len) = loop 0 s0
846+ where
847+ loop !i !s = case next s of
848+ Done -> i
849+ Skip s' -> loop i s'
850+ Yield x s' | a == x -> loop (i+1) s'
851+ | otherwise -> loop i s'
852+{-# INLINE [0] count #-}
853+
841-------------------------------------------------------------------------------
854-------------------------------------------------------------------------------
842-- * Zipping
855-- * Zipping
843
856
tests/Properties.hs+2
@@ -165,6 +165,7 @@ prop_findIndex p = L.findIndex p `eqP` T.findIndex p
165prop_findIndices p = L.findIndices p`eqP` T.findIndices p
165prop_findIndices p = L.findIndices p`eqP` T.findIndices p
166prop_elemIndex c = L.elemIndex c `eqP` T.elemIndex c
166prop_elemIndex c = L.elemIndex c `eqP` T.elemIndex c
167prop_elemIndices c = L.elemIndices c`eqP` T.elemIndices c
167prop_elemIndices c = L.elemIndices c`eqP` T.elemIndices c
168+prop_count c = (L.length . L.elemIndices c) `eqP` T.count c
168prop_zipWith c s = L.zipWith c s `eqP` (unpack . T.zipWith c (pack s))
169prop_zipWith c s = L.zipWith c s `eqP` (unpack . T.zipWith c (pack s))
169
170
170main = run tests =<< getArgs
171main = run tests =<< getArgs
@@ -269,5 +270,6 @@ tests = [
269 ("prop_findIndices", mytest prop_findIndices),
270 ("prop_findIndices", mytest prop_findIndices),
270 ("prop_elemIndex", mytest prop_elemIndex),
271 ("prop_elemIndex", mytest prop_elemIndex),
271 ("prop_elemIndices", mytest prop_elemIndices),
272 ("prop_elemIndices", mytest prop_elemIndices),
273+ ("prop_count", mytest prop_count),
272 ("prop_zipWith", mytest prop_zipWith)
274 ("prop_zipWith", mytest prop_zipWith)
273 ]
275 ]