From deacb97048b308c7df414946b40fb746826f550b Mon Sep 17 00:00:00 2001 From: Fintan Halpenny Date: Wed, 20 Dec 2017 12:00:58 +0000 Subject: [PATCH 01/11] Adding `safeIndex` to allow for indexing with a Maybe return value --- Data/ByteString.hs | 11 +++++++++++ Data/ByteString/Char8.hs | 8 ++++++++ Data/ByteString/Lazy.hs | 13 ++++++++++++ Data/ByteString/Lazy/Char8.hs | 8 ++++++++ tests/Properties.hs | 37 +++++++++++++++++++++++++++++++++++ 5 files changed, 77 insertions(+) diff --git a/Data/ByteString.hs b/Data/ByteString.hs index 801afcea8..6b732d124 100644 --- a/Data/ByteString.hs +++ b/Data/ByteString.hs @@ -154,6 +154,7 @@ module Data.ByteString ( -- * Indexing ByteStrings index, -- :: ByteString -> Int -> Word8 + safeIndex, -- :: ByteString -> Int -> Maybe Word8 elemIndex, -- :: Word8 -> ByteString -> Maybe Int elemIndices, -- :: Word8 -> ByteString -> [Int] elemIndexEnd, -- :: Word8 -> ByteString -> Maybe Int @@ -1097,6 +1098,16 @@ index ps n | otherwise = ps `unsafeIndex` n {-# INLINE index #-} +-- | 'ByteString' index that returns 'Nothing' if: +-- @n < 0@ +-- @n > length byteString@ +safeIndex :: ByteString -> Int -> Maybe Word8 +safeIndex ps n + | n < 0 = Nothing + | n >= length ps = Nothing + | otherwise = Just $ ps `unsafeIndex` n +{-# INLINE safeIndex #-} + -- | /O(n)/ The 'elemIndex' function returns the index of the first -- element in the given 'ByteString' which is equal to the query -- element, or 'Nothing' if there is no such element. diff --git a/Data/ByteString/Char8.hs b/Data/ByteString/Char8.hs index 6a01e6582..d91f0c9a0 100644 --- a/Data/ByteString/Char8.hs +++ b/Data/ByteString/Char8.hs @@ -164,6 +164,7 @@ module Data.ByteString.Char8 ( -- * Indexing ByteStrings index, -- :: ByteString -> Int -> Char + safeIndex, -- :: ByteString -> Int -> Maybe Char elemIndex, -- :: Char -> ByteString -> Maybe Int elemIndices, -- :: Char -> ByteString -> [Int] elemIndexEnd, -- :: Char -> ByteString -> Maybe Int @@ -644,6 +645,13 @@ index :: ByteString -> Int -> Char index = (w2c .) . B.index {-# INLINE index #-} +-- | 'ByteString' index that returns 'Nothing' if: +-- @n < 0@ +-- @n > length byteString@ +safeIndex :: ByteString -> Int -> Maybe Char +safeIndex = ((fmap w2c) .) . B.safeIndex +{-# INLINE safeIndex #-} + -- | /O(n)/ The 'elemIndex' function returns the index of the first -- element in the given 'ByteString' which is equal (by memchr) to the -- query element, or 'Nothing' if there is no such element. diff --git a/Data/ByteString/Lazy.hs b/Data/ByteString/Lazy.hs index 773894322..e7d35b627 100644 --- a/Data/ByteString/Lazy.hs +++ b/Data/ByteString/Lazy.hs @@ -167,6 +167,7 @@ module Data.ByteString.Lazy ( -- * Indexing ByteStrings index, -- :: ByteString -> Int64 -> Word8 + safeIndex, -- :: ByteString -> Int64 -> Maybe Word8 elemIndex, -- :: Word8 -> ByteString -> Maybe Int64 elemIndexEnd, -- :: Word8 -> ByteString -> Maybe Int64 elemIndices, -- :: Word8 -> ByteString -> [Int64] @@ -895,6 +896,18 @@ index cs0 i = index' cs0 i index' cs (n - fromIntegral (S.length c)) | otherwise = S.unsafeIndex c (fromIntegral n) +-- | 'ByteString' index that returns 'Nothing' if: +-- @n < 0@ +-- @n > length byteString@ +safeIndex :: ByteString -> Int64 -> Maybe Word8 +safeIndex _ i | i < 0 = Nothing +safeIndex cs0 i = index' cs0 i + where index' Empty b = Nothing + index' (Chunk c cs) n + | n >= fromIntegral (S.length c) = + index' cs (n - fromIntegral (S.length c)) + | otherwise = Just $ S.unsafeIndex c (fromIntegral n) + -- | /O(n)/ The 'elemIndex' function returns the index of the first -- element in the given 'ByteString' which is equal to the query -- element, or 'Nothing' if there is no such element. diff --git a/Data/ByteString/Lazy/Char8.hs b/Data/ByteString/Lazy/Char8.hs index 0a2cd8fb2..a4c870c30 100644 --- a/Data/ByteString/Lazy/Char8.hs +++ b/Data/ByteString/Lazy/Char8.hs @@ -146,6 +146,7 @@ module Data.ByteString.Lazy.Char8 ( -- * Indexing ByteStrings index, -- :: ByteString -> Int64 -> Char + safeIndex, -- :: ByteString -> Int64 -> Maybe Char elemIndex, -- :: Char -> ByteString -> Maybe Int64 elemIndices, -- :: Char -> ByteString -> [Int64] findIndex, -- :: (Char -> Bool) -> ByteString -> Maybe Int64 @@ -527,6 +528,13 @@ index :: ByteString -> Int64 -> Char index = (w2c .) . L.index {-# INLINE index #-} +-- | 'ByteString' index that returns 'Nothing' if: +-- @n < 0@ +-- @n > length byteString@ +safeIndex :: ByteString -> Int64 -> Maybe Char +safeIndex = ((fmap w2c) .) . L.safeIndex +{-# safeIndex #-} + -- | /O(n)/ The 'elemIndex' function returns the index of the first -- element in the given 'ByteString' which is equal (by memchr) to the -- query element, or 'Nothing' if there is no such element. diff --git a/tests/Properties.hs b/tests/Properties.hs index 16b57ba3c..5a9edfb25 100644 --- a/tests/Properties.hs +++ b/tests/Properties.hs @@ -788,6 +788,39 @@ prop_index_C (String8 xs) = forAll indices $ \i -> (xs !! i) == C.pack xs `C.index` (fromIntegral i) where indices = choose (0, length xs -1) +-- | Test 'safeIndex' for Lazy and Strict 'ByteString's. +-- If we are testing within the bounds it should return a 'Just' value. +-- If we are testing outside of the bounds it should return a 'Nothing' value. +prop_safeIndex_Just_L xs = + not (null xs) ==> + forAll indices $ \i -> isJust (ys `L.safeIndex` (fromIntegral i)) + where + ys = L.pack xs + indices = choose (0, length xs -1) + +prop_safeIndex_Just_P xs = + not (null xs) ==> + forAll indices $ \i -> isJust (ys `P.safeIndex` (fromIntegral i)) + where + ys = P.pack xs + indices = choose (0, length xs -1) + +prop_safeIndex_Nothing_L xs = + not (null xs) ==> + forAll indices $ \i -> isNothing (ys `L.safeIndex` (fromIntegral i)) + where + ys = L.pack xs + outOfBounds = choose (-100, length xs + 100) + indices = suchThat outOfBounds (\n -> n < 0 || n >= length xs) + +prop_safeIndex_Nothing_P xs = + not (null xs) ==> + forAll indices $ \i -> isNothing (ys `P.safeIndex` (fromIntegral i)) + where + ys = P.pack xs + outOfBounds = choose (-100, length xs + 100) + indices = suchThat outOfBounds (\n -> n < 0 || n >= length xs) + prop_elemIndex xs c = (elemIndex c xs) == fmap fromIntegral (L.elemIndex c (pack xs)) prop_elemIndexCL :: String8 -> Char8 -> Bool @@ -2439,6 +2472,10 @@ ll_tests = , testProperty "index" prop_index , testProperty "index" prop_index_D , testProperty "index" prop_index_C + , testProperty "safeIndex" prop_safeIndex_Just_P + , testProperty "safeIndex" prop_safeIndex_Just_L + , testProperty "safeIndex" prop_safeIndex_Nothing_P + , testProperty "safeIndex" prop_safeIndex_Nothing_L , testProperty "elemIndex" prop_elemIndex , testProperty "elemIndices" prop_elemIndices , testProperty "count/elemIndices" prop_count From 819f0de9bf2462c5f37c4b9d0dbffde80824e541 Mon Sep 17 00:00:00 2001 From: Fintan Halpenny Date: Fri, 19 Jan 2018 14:21:04 +0000 Subject: [PATCH 02/11] Renamed safeIndex to indexMay. Added operator !? --- Data/ByteString.hs | 13 +++++++++---- Data/ByteString/Char8.hs | 13 +++++++++---- Data/ByteString/Lazy.hs | 13 +++++++++---- Data/ByteString/Lazy/Char8.hs | 13 +++++++++---- tests/Properties.hs | 26 +++++++++++++------------- 5 files changed, 49 insertions(+), 29 deletions(-) diff --git a/Data/ByteString.hs b/Data/ByteString.hs index 6b732d124..e2a2e1206 100644 --- a/Data/ByteString.hs +++ b/Data/ByteString.hs @@ -154,7 +154,8 @@ module Data.ByteString ( -- * Indexing ByteStrings index, -- :: ByteString -> Int -> Word8 - safeIndex, -- :: ByteString -> Int -> Maybe Word8 + indexMay, -- :: ByteString -> Int -> Maybe Word8 + (!?), -- :: ByteString -> Int -> Maybe Word8 elemIndex, -- :: Word8 -> ByteString -> Maybe Int elemIndices, -- :: Word8 -> ByteString -> [Int] elemIndexEnd, -- :: Word8 -> ByteString -> Maybe Int @@ -1101,12 +1102,16 @@ index ps n -- | 'ByteString' index that returns 'Nothing' if: -- @n < 0@ -- @n > length byteString@ -safeIndex :: ByteString -> Int -> Maybe Word8 -safeIndex ps n +indexMay :: ByteString -> Int -> Maybe Word8 +indexMay ps n | n < 0 = Nothing | n >= length ps = Nothing | otherwise = Just $ ps `unsafeIndex` n -{-# INLINE safeIndex #-} +{-# INLINE indexMay #-} + +-- | Infix equivalent for `indexMay` +(!?) :: ByteString -> Int -> Maybe Word8 +(!?) = indexMay -- | /O(n)/ The 'elemIndex' function returns the index of the first -- element in the given 'ByteString' which is equal to the query diff --git a/Data/ByteString/Char8.hs b/Data/ByteString/Char8.hs index d91f0c9a0..9c78e3ce4 100644 --- a/Data/ByteString/Char8.hs +++ b/Data/ByteString/Char8.hs @@ -164,7 +164,8 @@ module Data.ByteString.Char8 ( -- * Indexing ByteStrings index, -- :: ByteString -> Int -> Char - safeIndex, -- :: ByteString -> Int -> Maybe Char + indexMay, -- :: ByteString -> Int -> Maybe Char + (!?), -- :: ByteString -> Int -> Maybe Char elemIndex, -- :: Char -> ByteString -> Maybe Int elemIndices, -- :: Char -> ByteString -> [Int] elemIndexEnd, -- :: Char -> ByteString -> Maybe Int @@ -648,9 +649,13 @@ index = (w2c .) . B.index -- | 'ByteString' index that returns 'Nothing' if: -- @n < 0@ -- @n > length byteString@ -safeIndex :: ByteString -> Int -> Maybe Char -safeIndex = ((fmap w2c) .) . B.safeIndex -{-# INLINE safeIndex #-} +indexMay :: ByteString -> Int -> Maybe Char +indexMay = ((fmap w2c) .) . B.indexMay +{-# INLINE indexMay #-} + +-- | Infix equivalent for `indexMay` +(!?) :: ByteString -> Int -> Maybe Char +(!?) = indexMay -- | /O(n)/ The 'elemIndex' function returns the index of the first -- element in the given 'ByteString' which is equal (by memchr) to the diff --git a/Data/ByteString/Lazy.hs b/Data/ByteString/Lazy.hs index e7d35b627..bead2a849 100644 --- a/Data/ByteString/Lazy.hs +++ b/Data/ByteString/Lazy.hs @@ -167,7 +167,8 @@ module Data.ByteString.Lazy ( -- * Indexing ByteStrings index, -- :: ByteString -> Int64 -> Word8 - safeIndex, -- :: ByteString -> Int64 -> Maybe Word8 + indexMay, -- :: ByteString -> Int64 -> Maybe Word8 + (!?), -- :: ByteString -> Int64 -> Maybe Word8 elemIndex, -- :: Word8 -> ByteString -> Maybe Int64 elemIndexEnd, -- :: Word8 -> ByteString -> Maybe Int64 elemIndices, -- :: Word8 -> ByteString -> [Int64] @@ -899,15 +900,19 @@ index cs0 i = index' cs0 i -- | 'ByteString' index that returns 'Nothing' if: -- @n < 0@ -- @n > length byteString@ -safeIndex :: ByteString -> Int64 -> Maybe Word8 -safeIndex _ i | i < 0 = Nothing -safeIndex cs0 i = index' cs0 i +indexMay :: ByteString -> Int64 -> Maybe Word8 +indexMay _ i | i < 0 = Nothing +indexMay cs0 i = index' cs0 i where index' Empty b = Nothing index' (Chunk c cs) n | n >= fromIntegral (S.length c) = index' cs (n - fromIntegral (S.length c)) | otherwise = Just $ S.unsafeIndex c (fromIntegral n) +-- | Infix equivalent for `indexMay` +(!?) :: ByteString -> Int64 -> Maybe Word8 +(!?) = indexMay + -- | /O(n)/ The 'elemIndex' function returns the index of the first -- element in the given 'ByteString' which is equal to the query -- element, or 'Nothing' if there is no such element. diff --git a/Data/ByteString/Lazy/Char8.hs b/Data/ByteString/Lazy/Char8.hs index a4c870c30..c5542cced 100644 --- a/Data/ByteString/Lazy/Char8.hs +++ b/Data/ByteString/Lazy/Char8.hs @@ -146,7 +146,8 @@ module Data.ByteString.Lazy.Char8 ( -- * Indexing ByteStrings index, -- :: ByteString -> Int64 -> Char - safeIndex, -- :: ByteString -> Int64 -> Maybe Char + indexMay, -- :: ByteString -> Int64 -> Maybe Char + (!?), -- :: ByteString -> Int64 -> Maybe Char elemIndex, -- :: Char -> ByteString -> Maybe Int64 elemIndices, -- :: Char -> ByteString -> [Int64] findIndex, -- :: (Char -> Bool) -> ByteString -> Maybe Int64 @@ -531,9 +532,13 @@ index = (w2c .) . L.index -- | 'ByteString' index that returns 'Nothing' if: -- @n < 0@ -- @n > length byteString@ -safeIndex :: ByteString -> Int64 -> Maybe Char -safeIndex = ((fmap w2c) .) . L.safeIndex -{-# safeIndex #-} +indexMay :: ByteString -> Int64 -> Maybe Char +indexMay = ((fmap w2c) .) . L.indexMay +{-# indexMay #-} + +-- | Infix equivalent for `indexMay` +(!?) :: ByteString -> Int64 -> Maybe Char +(!?) = indexMay -- | /O(n)/ The 'elemIndex' function returns the index of the first -- element in the given 'ByteString' which is equal (by memchr) to the diff --git a/tests/Properties.hs b/tests/Properties.hs index 5a9edfb25..deab8ffea 100644 --- a/tests/Properties.hs +++ b/tests/Properties.hs @@ -788,34 +788,34 @@ prop_index_C (String8 xs) = forAll indices $ \i -> (xs !! i) == C.pack xs `C.index` (fromIntegral i) where indices = choose (0, length xs -1) --- | Test 'safeIndex' for Lazy and Strict 'ByteString's. +-- | Test 'indexMay for Lazy and Strict 'ByteString's. -- If we are testing within the bounds it should return a 'Just' value. -- If we are testing outside of the bounds it should return a 'Nothing' value. -prop_safeIndex_Just_L xs = +prop_indexMay_Just_L xs = not (null xs) ==> - forAll indices $ \i -> isJust (ys `L.safeIndex` (fromIntegral i)) + forAll indices $ \i -> isJust (ys `L.indexMay` (fromIntegral i)) where ys = L.pack xs indices = choose (0, length xs -1) -prop_safeIndex_Just_P xs = +prop_indexMay_Just_P xs = not (null xs) ==> - forAll indices $ \i -> isJust (ys `P.safeIndex` (fromIntegral i)) + forAll indices $ \i -> isJust (ys `P.indexMay` (fromIntegral i)) where ys = P.pack xs indices = choose (0, length xs -1) -prop_safeIndex_Nothing_L xs = +prop_indexMay_Nothing_L xs = not (null xs) ==> - forAll indices $ \i -> isNothing (ys `L.safeIndex` (fromIntegral i)) + forAll indices $ \i -> isNothing (ys `L.indexMay` (fromIntegral i)) where ys = L.pack xs outOfBounds = choose (-100, length xs + 100) indices = suchThat outOfBounds (\n -> n < 0 || n >= length xs) -prop_safeIndex_Nothing_P xs = +prop_indexMay_Nothing_P xs = not (null xs) ==> - forAll indices $ \i -> isNothing (ys `P.safeIndex` (fromIntegral i)) + forAll indices $ \i -> isNothing (ys `P.indexMay` (fromIntegral i)) where ys = P.pack xs outOfBounds = choose (-100, length xs + 100) @@ -2472,10 +2472,10 @@ ll_tests = , testProperty "index" prop_index , testProperty "index" prop_index_D , testProperty "index" prop_index_C - , testProperty "safeIndex" prop_safeIndex_Just_P - , testProperty "safeIndex" prop_safeIndex_Just_L - , testProperty "safeIndex" prop_safeIndex_Nothing_P - , testProperty "safeIndex" prop_safeIndex_Nothing_L + , testProperty "indexMay" prop_indexMay_Just_P + , testProperty "indexMay" prop_indexMay_Just_L + , testProperty "indexMay" prop_indexMay_Nothing_P + , testProperty "indexMay" prop_indexMay_Nothing_L , testProperty "elemIndex" prop_elemIndex , testProperty "elemIndices" prop_elemIndices , testProperty "count/elemIndices" prop_count From cf444fbb003c44a196cb76e0ea32f02467593329 Mon Sep 17 00:00:00 2001 From: Fintan Halpenny Date: Fri, 19 Jan 2018 15:08:51 +0000 Subject: [PATCH 03/11] Renamed indexMay to indexMaybe --- Data/ByteString.hs | 12 ++++++------ Data/ByteString/Char8.hs | 12 ++++++------ Data/ByteString/Lazy.hs | 12 ++++++------ Data/ByteString/Lazy/Char8.hs | 12 ++++++------ tests/Properties.hs | 26 +++++++++++++------------- 5 files changed, 37 insertions(+), 37 deletions(-) diff --git a/Data/ByteString.hs b/Data/ByteString.hs index e2a2e1206..f9d2f34ee 100644 --- a/Data/ByteString.hs +++ b/Data/ByteString.hs @@ -154,7 +154,7 @@ module Data.ByteString ( -- * Indexing ByteStrings index, -- :: ByteString -> Int -> Word8 - indexMay, -- :: ByteString -> Int -> Maybe Word8 + indexMaybe, -- :: ByteString -> Int -> Maybe Word8 (!?), -- :: ByteString -> Int -> Maybe Word8 elemIndex, -- :: Word8 -> ByteString -> Maybe Int elemIndices, -- :: Word8 -> ByteString -> [Int] @@ -1102,16 +1102,16 @@ index ps n -- | 'ByteString' index that returns 'Nothing' if: -- @n < 0@ -- @n > length byteString@ -indexMay :: ByteString -> Int -> Maybe Word8 -indexMay ps n +indexMaybe :: ByteString -> Int -> Maybe Word8 +indexMaybe ps n | n < 0 = Nothing | n >= length ps = Nothing | otherwise = Just $ ps `unsafeIndex` n -{-# INLINE indexMay #-} +{-# INLINE indexMaybe #-} --- | Infix equivalent for `indexMay` +-- | Infix equivalent for `indexMaybe` (!?) :: ByteString -> Int -> Maybe Word8 -(!?) = indexMay +(!?) = indexMaybe -- | /O(n)/ The 'elemIndex' function returns the index of the first -- element in the given 'ByteString' which is equal to the query diff --git a/Data/ByteString/Char8.hs b/Data/ByteString/Char8.hs index 9c78e3ce4..daee1cc4a 100644 --- a/Data/ByteString/Char8.hs +++ b/Data/ByteString/Char8.hs @@ -164,7 +164,7 @@ module Data.ByteString.Char8 ( -- * Indexing ByteStrings index, -- :: ByteString -> Int -> Char - indexMay, -- :: ByteString -> Int -> Maybe Char + indexMaybe, -- :: ByteString -> Int -> Maybe Char (!?), -- :: ByteString -> Int -> Maybe Char elemIndex, -- :: Char -> ByteString -> Maybe Int elemIndices, -- :: Char -> ByteString -> [Int] @@ -649,13 +649,13 @@ index = (w2c .) . B.index -- | 'ByteString' index that returns 'Nothing' if: -- @n < 0@ -- @n > length byteString@ -indexMay :: ByteString -> Int -> Maybe Char -indexMay = ((fmap w2c) .) . B.indexMay -{-# INLINE indexMay #-} +indexMaybe :: ByteString -> Int -> Maybe Char +indexMaybe = ((fmap w2c) .) . B.indexMaybe +{-# INLINE indexMaybe #-} --- | Infix equivalent for `indexMay` +-- | Infix equivalent for `indexMaybe` (!?) :: ByteString -> Int -> Maybe Char -(!?) = indexMay +(!?) = indexMaybe -- | /O(n)/ The 'elemIndex' function returns the index of the first -- element in the given 'ByteString' which is equal (by memchr) to the diff --git a/Data/ByteString/Lazy.hs b/Data/ByteString/Lazy.hs index bead2a849..f89c15064 100644 --- a/Data/ByteString/Lazy.hs +++ b/Data/ByteString/Lazy.hs @@ -167,7 +167,7 @@ module Data.ByteString.Lazy ( -- * Indexing ByteStrings index, -- :: ByteString -> Int64 -> Word8 - indexMay, -- :: ByteString -> Int64 -> Maybe Word8 + indexMaybe, -- :: ByteString -> Int64 -> Maybe Word8 (!?), -- :: ByteString -> Int64 -> Maybe Word8 elemIndex, -- :: Word8 -> ByteString -> Maybe Int64 elemIndexEnd, -- :: Word8 -> ByteString -> Maybe Int64 @@ -900,18 +900,18 @@ index cs0 i = index' cs0 i -- | 'ByteString' index that returns 'Nothing' if: -- @n < 0@ -- @n > length byteString@ -indexMay :: ByteString -> Int64 -> Maybe Word8 -indexMay _ i | i < 0 = Nothing -indexMay cs0 i = index' cs0 i +indexMaybe :: ByteString -> Int64 -> Maybe Word8 +indexMaybe _ i | i < 0 = Nothing +indexMaybe cs0 i = index' cs0 i where index' Empty b = Nothing index' (Chunk c cs) n | n >= fromIntegral (S.length c) = index' cs (n - fromIntegral (S.length c)) | otherwise = Just $ S.unsafeIndex c (fromIntegral n) --- | Infix equivalent for `indexMay` +-- | Infix equivalent for `indexMaybe` (!?) :: ByteString -> Int64 -> Maybe Word8 -(!?) = indexMay +(!?) = indexMaybe -- | /O(n)/ The 'elemIndex' function returns the index of the first -- element in the given 'ByteString' which is equal to the query diff --git a/Data/ByteString/Lazy/Char8.hs b/Data/ByteString/Lazy/Char8.hs index c5542cced..5882cbb28 100644 --- a/Data/ByteString/Lazy/Char8.hs +++ b/Data/ByteString/Lazy/Char8.hs @@ -146,7 +146,7 @@ module Data.ByteString.Lazy.Char8 ( -- * Indexing ByteStrings index, -- :: ByteString -> Int64 -> Char - indexMay, -- :: ByteString -> Int64 -> Maybe Char + indexMaybe, -- :: ByteString -> Int64 -> Maybe Char (!?), -- :: ByteString -> Int64 -> Maybe Char elemIndex, -- :: Char -> ByteString -> Maybe Int64 elemIndices, -- :: Char -> ByteString -> [Int64] @@ -532,13 +532,13 @@ index = (w2c .) . L.index -- | 'ByteString' index that returns 'Nothing' if: -- @n < 0@ -- @n > length byteString@ -indexMay :: ByteString -> Int64 -> Maybe Char -indexMay = ((fmap w2c) .) . L.indexMay -{-# indexMay #-} +indexMaybe :: ByteString -> Int64 -> Maybe Char +indexMaybe = ((fmap w2c) .) . L.indexMaybe +{-# indexMaybe #-} --- | Infix equivalent for `indexMay` +-- | Infix equivalent for `indexMaybe` (!?) :: ByteString -> Int64 -> Maybe Char -(!?) = indexMay +(!?) = indexMaybe -- | /O(n)/ The 'elemIndex' function returns the index of the first -- element in the given 'ByteString' which is equal (by memchr) to the diff --git a/tests/Properties.hs b/tests/Properties.hs index deab8ffea..ddc08dd96 100644 --- a/tests/Properties.hs +++ b/tests/Properties.hs @@ -788,34 +788,34 @@ prop_index_C (String8 xs) = forAll indices $ \i -> (xs !! i) == C.pack xs `C.index` (fromIntegral i) where indices = choose (0, length xs -1) --- | Test 'indexMay for Lazy and Strict 'ByteString's. +-- | Test 'indexMaybe for Lazy and Strict 'ByteString's. -- If we are testing within the bounds it should return a 'Just' value. -- If we are testing outside of the bounds it should return a 'Nothing' value. -prop_indexMay_Just_L xs = +prop_indexMaybe_Just_L xs = not (null xs) ==> - forAll indices $ \i -> isJust (ys `L.indexMay` (fromIntegral i)) + forAll indices $ \i -> isJust (ys `L.indexMaybe` (fromIntegral i)) where ys = L.pack xs indices = choose (0, length xs -1) -prop_indexMay_Just_P xs = +prop_indexMaybe_Just_P xs = not (null xs) ==> - forAll indices $ \i -> isJust (ys `P.indexMay` (fromIntegral i)) + forAll indices $ \i -> isJust (ys `P.indexMaybe` (fromIntegral i)) where ys = P.pack xs indices = choose (0, length xs -1) -prop_indexMay_Nothing_L xs = +prop_indexMaybe_Nothing_L xs = not (null xs) ==> - forAll indices $ \i -> isNothing (ys `L.indexMay` (fromIntegral i)) + forAll indices $ \i -> isNothing (ys `L.indexMaybe` (fromIntegral i)) where ys = L.pack xs outOfBounds = choose (-100, length xs + 100) indices = suchThat outOfBounds (\n -> n < 0 || n >= length xs) -prop_indexMay_Nothing_P xs = +prop_indexMaybe_Nothing_P xs = not (null xs) ==> - forAll indices $ \i -> isNothing (ys `P.indexMay` (fromIntegral i)) + forAll indices $ \i -> isNothing (ys `P.indexMaybe` (fromIntegral i)) where ys = P.pack xs outOfBounds = choose (-100, length xs + 100) @@ -2472,10 +2472,10 @@ ll_tests = , testProperty "index" prop_index , testProperty "index" prop_index_D , testProperty "index" prop_index_C - , testProperty "indexMay" prop_indexMay_Just_P - , testProperty "indexMay" prop_indexMay_Just_L - , testProperty "indexMay" prop_indexMay_Nothing_P - , testProperty "indexMay" prop_indexMay_Nothing_L + , testProperty "indexMaybe" prop_indexMaybe_Just_P + , testProperty "indexMaybe" prop_indexMaybe_Just_L + , testProperty "indexMaybe" prop_indexMaybe_Nothing_P + , testProperty "indexMaybe" prop_indexMaybe_Nothing_L , testProperty "elemIndex" prop_elemIndex , testProperty "elemIndices" prop_elemIndices , testProperty "count/elemIndices" prop_count From e0c724eb9d55a76336fb709534f95d317f0d1b6f Mon Sep 17 00:00:00 2001 From: Fintan Halpenny Date: Wed, 24 Jan 2018 16:13:19 +0000 Subject: [PATCH 04/11] Fixed documentation. Added change to changelog. --- Changelog.md | 1 + Data/ByteString.hs | 13 +++++-------- Data/ByteString/Char8.hs | 13 +++++-------- Data/ByteString/Lazy.hs | 13 +++++-------- Data/ByteString/Lazy/Char8.hs | 13 +++++-------- 5 files changed, 21 insertions(+), 32 deletions(-) diff --git a/Changelog.md b/Changelog.md index 4f04b355e..3ce85f350 100644 --- a/Changelog.md +++ b/Changelog.md @@ -9,6 +9,7 @@ * [Add `IsList` instances for strict and lazy `ByteString` and for `ShortByteString`](https://github.com/haskell/bytestring/pull/219) * [Add `createUpToN'` and `unsafeCreateUpToN'` to `Data.ByteString.Internal`](https://github.com/haskell/bytestring/pull/245) * [Add `boundedPrim` to `Data.ByteString.Builder.Prim.Internal` and deprecate `boudedPrim`](https://github.com/haskell/bytestring/pull/246) + * Add `indexMaybe` for indexing that returns `Maybe` * [Deprecate the `Data.ByteString.Lazy.Builder` and `Data.ByteString.Lazy.Builder.{ASCII,Extras}` modules](https://github.com/haskell/bytestring/pull/250) * [Fix documented complexity of `Data.ByteString.Lazy.length`](https://github.com/haskell/bytestring/pull/255) * [Assorted documentation fixes](https://github.com/haskell/bytestring/pull/248) diff --git a/Data/ByteString.hs b/Data/ByteString.hs index f9d2f34ee..9642114a9 100644 --- a/Data/ByteString.hs +++ b/Data/ByteString.hs @@ -155,7 +155,6 @@ module Data.ByteString ( -- * Indexing ByteStrings index, -- :: ByteString -> Int -> Word8 indexMaybe, -- :: ByteString -> Int -> Maybe Word8 - (!?), -- :: ByteString -> Int -> Maybe Word8 elemIndex, -- :: Word8 -> ByteString -> Maybe Int elemIndices, -- :: Word8 -> ByteString -> [Int] elemIndexEnd, -- :: Word8 -> ByteString -> Maybe Int @@ -1099,9 +1098,11 @@ index ps n | otherwise = ps `unsafeIndex` n {-# INLINE index #-} --- | 'ByteString' index that returns 'Nothing' if: --- @n < 0@ --- @n > length byteString@ +-- | /O(1)/ 'ByteString' index, starting from 0, that returns 'Nothing' if: +-- +-- > 0 <= n < length bs +-- +-- @since 0.10.10.0 indexMaybe :: ByteString -> Int -> Maybe Word8 indexMaybe ps n | n < 0 = Nothing @@ -1109,10 +1110,6 @@ indexMaybe ps n | otherwise = Just $ ps `unsafeIndex` n {-# INLINE indexMaybe #-} --- | Infix equivalent for `indexMaybe` -(!?) :: ByteString -> Int -> Maybe Word8 -(!?) = indexMaybe - -- | /O(n)/ The 'elemIndex' function returns the index of the first -- element in the given 'ByteString' which is equal to the query -- element, or 'Nothing' if there is no such element. diff --git a/Data/ByteString/Char8.hs b/Data/ByteString/Char8.hs index daee1cc4a..147beeaa8 100644 --- a/Data/ByteString/Char8.hs +++ b/Data/ByteString/Char8.hs @@ -165,7 +165,6 @@ module Data.ByteString.Char8 ( -- * Indexing ByteStrings index, -- :: ByteString -> Int -> Char indexMaybe, -- :: ByteString -> Int -> Maybe Char - (!?), -- :: ByteString -> Int -> Maybe Char elemIndex, -- :: Char -> ByteString -> Maybe Int elemIndices, -- :: Char -> ByteString -> [Int] elemIndexEnd, -- :: Char -> ByteString -> Maybe Int @@ -646,17 +645,15 @@ index :: ByteString -> Int -> Char index = (w2c .) . B.index {-# INLINE index #-} --- | 'ByteString' index that returns 'Nothing' if: --- @n < 0@ --- @n > length byteString@ +-- | /O(1)/ 'ByteString' index, starting from 0, that returns 'Nothing' if: +-- +-- > 0 <= n < length bs +-- +-- @since 0.10.10.0 indexMaybe :: ByteString -> Int -> Maybe Char indexMaybe = ((fmap w2c) .) . B.indexMaybe {-# INLINE indexMaybe #-} --- | Infix equivalent for `indexMaybe` -(!?) :: ByteString -> Int -> Maybe Char -(!?) = indexMaybe - -- | /O(n)/ The 'elemIndex' function returns the index of the first -- element in the given 'ByteString' which is equal (by memchr) to the -- query element, or 'Nothing' if there is no such element. diff --git a/Data/ByteString/Lazy.hs b/Data/ByteString/Lazy.hs index f89c15064..a6917919d 100644 --- a/Data/ByteString/Lazy.hs +++ b/Data/ByteString/Lazy.hs @@ -168,7 +168,6 @@ module Data.ByteString.Lazy ( -- * Indexing ByteStrings index, -- :: ByteString -> Int64 -> Word8 indexMaybe, -- :: ByteString -> Int64 -> Maybe Word8 - (!?), -- :: ByteString -> Int64 -> Maybe Word8 elemIndex, -- :: Word8 -> ByteString -> Maybe Int64 elemIndexEnd, -- :: Word8 -> ByteString -> Maybe Int64 elemIndices, -- :: Word8 -> ByteString -> [Int64] @@ -897,9 +896,11 @@ index cs0 i = index' cs0 i index' cs (n - fromIntegral (S.length c)) | otherwise = S.unsafeIndex c (fromIntegral n) --- | 'ByteString' index that returns 'Nothing' if: --- @n < 0@ --- @n > length byteString@ +-- | /O(c)/ 'ByteString' index, starting from 0, that returns 'Nothing' if: +-- +-- > 0 <= n < length bs +-- +-- @since 0.10.10.0 indexMaybe :: ByteString -> Int64 -> Maybe Word8 indexMaybe _ i | i < 0 = Nothing indexMaybe cs0 i = index' cs0 i @@ -909,10 +910,6 @@ indexMaybe cs0 i = index' cs0 i index' cs (n - fromIntegral (S.length c)) | otherwise = Just $ S.unsafeIndex c (fromIntegral n) --- | Infix equivalent for `indexMaybe` -(!?) :: ByteString -> Int64 -> Maybe Word8 -(!?) = indexMaybe - -- | /O(n)/ The 'elemIndex' function returns the index of the first -- element in the given 'ByteString' which is equal to the query -- element, or 'Nothing' if there is no such element. diff --git a/Data/ByteString/Lazy/Char8.hs b/Data/ByteString/Lazy/Char8.hs index 5882cbb28..d68a7a3fc 100644 --- a/Data/ByteString/Lazy/Char8.hs +++ b/Data/ByteString/Lazy/Char8.hs @@ -147,7 +147,6 @@ module Data.ByteString.Lazy.Char8 ( -- * Indexing ByteStrings index, -- :: ByteString -> Int64 -> Char indexMaybe, -- :: ByteString -> Int64 -> Maybe Char - (!?), -- :: ByteString -> Int64 -> Maybe Char elemIndex, -- :: Char -> ByteString -> Maybe Int64 elemIndices, -- :: Char -> ByteString -> [Int64] findIndex, -- :: (Char -> Bool) -> ByteString -> Maybe Int64 @@ -529,17 +528,15 @@ index :: ByteString -> Int64 -> Char index = (w2c .) . L.index {-# INLINE index #-} --- | 'ByteString' index that returns 'Nothing' if: --- @n < 0@ --- @n > length byteString@ +-- | /O(1)/ 'ByteString' index, starting from 0, that returns 'Nothing' if: +-- +-- > 0 <= n < length bs +-- +-- @since 0.10.10.0 indexMaybe :: ByteString -> Int64 -> Maybe Char indexMaybe = ((fmap w2c) .) . L.indexMaybe {-# indexMaybe #-} --- | Infix equivalent for `indexMaybe` -(!?) :: ByteString -> Int64 -> Maybe Char -(!?) = indexMaybe - -- | /O(n)/ The 'elemIndex' function returns the index of the first -- element in the given 'ByteString' which is equal (by memchr) to the -- query element, or 'Nothing' if there is no such element. From 32c6ed84996d7db2a6e67a65e33208c9ebbfe9e7 Mon Sep 17 00:00:00 2001 From: FintanH Date: Sat, 16 May 2020 15:33:38 +0100 Subject: [PATCH 05/11] Fix documentation --- Data/ByteString.hs | 2 +- Data/ByteString/Char8.hs | 2 +- Data/ByteString/Lazy.hs | 4 ++-- Data/ByteString/Lazy/Char8.hs | 4 ++-- tests/Properties.hs | 2 +- 5 files changed, 7 insertions(+), 7 deletions(-) diff --git a/Data/ByteString.hs b/Data/ByteString.hs index 9642114a9..bb1be36a6 100644 --- a/Data/ByteString.hs +++ b/Data/ByteString.hs @@ -1098,7 +1098,7 @@ index ps n | otherwise = ps `unsafeIndex` n {-# INLINE index #-} --- | /O(1)/ 'ByteString' index, starting from 0, that returns 'Nothing' if: +-- | /O(1)/ 'ByteString' index, starting from 0, that returns 'Just' if: -- -- > 0 <= n < length bs -- diff --git a/Data/ByteString/Char8.hs b/Data/ByteString/Char8.hs index 147beeaa8..2884e3771 100644 --- a/Data/ByteString/Char8.hs +++ b/Data/ByteString/Char8.hs @@ -645,7 +645,7 @@ index :: ByteString -> Int -> Char index = (w2c .) . B.index {-# INLINE index #-} --- | /O(1)/ 'ByteString' index, starting from 0, that returns 'Nothing' if: +-- | /O(1)/ 'ByteString' index, starting from 0, that returns 'Just' if: -- -- > 0 <= n < length bs -- diff --git a/Data/ByteString/Lazy.hs b/Data/ByteString/Lazy.hs index a6917919d..e264be4e8 100644 --- a/Data/ByteString/Lazy.hs +++ b/Data/ByteString/Lazy.hs @@ -896,7 +896,7 @@ index cs0 i = index' cs0 i index' cs (n - fromIntegral (S.length c)) | otherwise = S.unsafeIndex c (fromIntegral n) --- | /O(c)/ 'ByteString' index, starting from 0, that returns 'Nothing' if: +-- | /O(c)/ 'ByteString' index, starting from 0, that returns 'Just' if: -- -- > 0 <= n < length bs -- @@ -904,7 +904,7 @@ index cs0 i = index' cs0 i indexMaybe :: ByteString -> Int64 -> Maybe Word8 indexMaybe _ i | i < 0 = Nothing indexMaybe cs0 i = index' cs0 i - where index' Empty b = Nothing + where index' Empty _ = Nothing index' (Chunk c cs) n | n >= fromIntegral (S.length c) = index' cs (n - fromIntegral (S.length c)) diff --git a/Data/ByteString/Lazy/Char8.hs b/Data/ByteString/Lazy/Char8.hs index d68a7a3fc..de06713bb 100644 --- a/Data/ByteString/Lazy/Char8.hs +++ b/Data/ByteString/Lazy/Char8.hs @@ -528,14 +528,14 @@ index :: ByteString -> Int64 -> Char index = (w2c .) . L.index {-# INLINE index #-} --- | /O(1)/ 'ByteString' index, starting from 0, that returns 'Nothing' if: +-- | /O(1)/ 'ByteString' index, starting from 0, that returns 'Just' if: -- -- > 0 <= n < length bs -- -- @since 0.10.10.0 indexMaybe :: ByteString -> Int64 -> Maybe Char indexMaybe = ((fmap w2c) .) . L.indexMaybe -{-# indexMaybe #-} +{-# INLINE indexMaybe #-} -- | /O(n)/ The 'elemIndex' function returns the index of the first -- element in the given 'ByteString' which is equal (by memchr) to the diff --git a/tests/Properties.hs b/tests/Properties.hs index ddc08dd96..eb5ca31d1 100644 --- a/tests/Properties.hs +++ b/tests/Properties.hs @@ -788,7 +788,7 @@ prop_index_C (String8 xs) = forAll indices $ \i -> (xs !! i) == C.pack xs `C.index` (fromIntegral i) where indices = choose (0, length xs -1) --- | Test 'indexMaybe for Lazy and Strict 'ByteString's. +-- | Test 'indexMaybe' for Lazy and Strict 'ByteString's. -- If we are testing within the bounds it should return a 'Just' value. -- If we are testing outside of the bounds it should return a 'Nothing' value. prop_indexMaybe_Just_L xs = From f2e918c70f675b026cdf6af788457612268cb98a Mon Sep 17 00:00:00 2001 From: FintanH Date: Sat, 16 May 2020 15:47:09 +0100 Subject: [PATCH 06/11] Add synonym for indexMaybe --- Data/ByteString.hs | 10 ++++++++++ Data/ByteString/Char8.hs | 10 ++++++++++ Data/ByteString/Lazy.hs | 10 ++++++++++ Data/ByteString/Lazy/Char8.hs | 10 ++++++++++ 4 files changed, 40 insertions(+) diff --git a/Data/ByteString.hs b/Data/ByteString.hs index bb1be36a6..a6c1b8bfb 100644 --- a/Data/ByteString.hs +++ b/Data/ByteString.hs @@ -155,6 +155,7 @@ module Data.ByteString ( -- * Indexing ByteStrings index, -- :: ByteString -> Int -> Word8 indexMaybe, -- :: ByteString -> Int -> Maybe Word8 + (!?), -- :: ByteString -> Int -> Maybe Word8 elemIndex, -- :: Word8 -> ByteString -> Maybe Int elemIndices, -- :: Word8 -> ByteString -> [Int] elemIndexEnd, -- :: Word8 -> ByteString -> Maybe Int @@ -1110,6 +1111,15 @@ indexMaybe ps n | otherwise = Just $ ps `unsafeIndex` n {-# INLINE indexMaybe #-} +-- | /O(1)/ 'ByteString' index, starting from 0, that returns 'Just' if: +-- +-- > 0 <= n < length bs +-- +-- @since 0.10.10.0 +(!?) :: ByteString -> Int -> Maybe Word8 +(!?) = indexMaybe +{-# INLINE (!?) #-} + -- | /O(n)/ The 'elemIndex' function returns the index of the first -- element in the given 'ByteString' which is equal to the query -- element, or 'Nothing' if there is no such element. diff --git a/Data/ByteString/Char8.hs b/Data/ByteString/Char8.hs index 2884e3771..466468c11 100644 --- a/Data/ByteString/Char8.hs +++ b/Data/ByteString/Char8.hs @@ -165,6 +165,7 @@ module Data.ByteString.Char8 ( -- * Indexing ByteStrings index, -- :: ByteString -> Int -> Char indexMaybe, -- :: ByteString -> Int -> Maybe Char + (!?), -- :: ByteString -> Int -> Maybe Char elemIndex, -- :: Char -> ByteString -> Maybe Int elemIndices, -- :: Char -> ByteString -> [Int] elemIndexEnd, -- :: Char -> ByteString -> Maybe Int @@ -654,6 +655,15 @@ indexMaybe :: ByteString -> Int -> Maybe Char indexMaybe = ((fmap w2c) .) . B.indexMaybe {-# INLINE indexMaybe #-} +-- | /O(1)/ 'ByteString' index, starting from 0, that returns 'Just' if: +-- +-- > 0 <= n < length bs +-- +-- @since 0.10.10.0 +(!?) :: ByteString -> Int -> Maybe Char +(!?) = indexMaybe +{-# INLINE (!?) #-} + -- | /O(n)/ The 'elemIndex' function returns the index of the first -- element in the given 'ByteString' which is equal (by memchr) to the -- query element, or 'Nothing' if there is no such element. diff --git a/Data/ByteString/Lazy.hs b/Data/ByteString/Lazy.hs index e264be4e8..a434820a9 100644 --- a/Data/ByteString/Lazy.hs +++ b/Data/ByteString/Lazy.hs @@ -168,6 +168,7 @@ module Data.ByteString.Lazy ( -- * Indexing ByteStrings index, -- :: ByteString -> Int64 -> Word8 indexMaybe, -- :: ByteString -> Int64 -> Maybe Word8 + (!?), -- :: ByteString -> Int64 -> Maybe Word8 elemIndex, -- :: Word8 -> ByteString -> Maybe Int64 elemIndexEnd, -- :: Word8 -> ByteString -> Maybe Int64 elemIndices, -- :: Word8 -> ByteString -> [Int64] @@ -910,6 +911,15 @@ indexMaybe cs0 i = index' cs0 i index' cs (n - fromIntegral (S.length c)) | otherwise = Just $ S.unsafeIndex c (fromIntegral n) +-- | /O(1)/ 'ByteString' index, starting from 0, that returns 'Just' if: +-- +-- > 0 <= n < length bs +-- +-- @since 0.10.10.0 +(!?) :: ByteString -> Int64 -> Maybe Word8 +(!?) = indexMaybe +{-# INLINE (!?) #-} + -- | /O(n)/ The 'elemIndex' function returns the index of the first -- element in the given 'ByteString' which is equal to the query -- element, or 'Nothing' if there is no such element. diff --git a/Data/ByteString/Lazy/Char8.hs b/Data/ByteString/Lazy/Char8.hs index de06713bb..a41a3902d 100644 --- a/Data/ByteString/Lazy/Char8.hs +++ b/Data/ByteString/Lazy/Char8.hs @@ -147,6 +147,7 @@ module Data.ByteString.Lazy.Char8 ( -- * Indexing ByteStrings index, -- :: ByteString -> Int64 -> Char indexMaybe, -- :: ByteString -> Int64 -> Maybe Char + (!?), -- :: ByteString -> Int64 -> Maybe Char elemIndex, -- :: Char -> ByteString -> Maybe Int64 elemIndices, -- :: Char -> ByteString -> [Int64] findIndex, -- :: (Char -> Bool) -> ByteString -> Maybe Int64 @@ -537,6 +538,15 @@ indexMaybe :: ByteString -> Int64 -> Maybe Char indexMaybe = ((fmap w2c) .) . L.indexMaybe {-# INLINE indexMaybe #-} +-- | /O(1)/ 'ByteString' index, starting from 0, that returns 'Just' if: +-- +-- > 0 <= n < length bs +-- +-- @since 0.10.10.0 +(!?) :: ByteString -> Int64 -> Maybe Char +(!?) = indexMaybe +{-# INLINE (!?) #-} + -- | /O(n)/ The 'elemIndex' function returns the index of the first -- element in the given 'ByteString' which is equal (by memchr) to the -- query element, or 'Nothing' if there is no such element. From d755b17ef3367d14fc7d45efa793234c0722f4d3 Mon Sep 17 00:00:00 2001 From: FintanH Date: Sat, 16 May 2020 15:51:41 +0100 Subject: [PATCH 07/11] Add indexMaybe and synonym to ShortByteString --- Data/ByteString/Short.hs | 2 +- Data/ByteString/Short/Internal.hs | 23 +++++++++++++++++++++-- 2 files changed, 22 insertions(+), 3 deletions(-) diff --git a/Data/ByteString/Short.hs b/Data/ByteString/Short.hs index b88a6a9a9..1b34f3583 100644 --- a/Data/ByteString/Short.hs +++ b/Data/ByteString/Short.hs @@ -77,7 +77,7 @@ module Data.ByteString.Short ( unpack, -- * Other operations - empty, null, length, index, + empty, null, length, index, indexMaybe, (!?), -- * Low level conversions -- ** Packing 'Foreign.C.String.CString's and pointers diff --git a/Data/ByteString/Short/Internal.hs b/Data/ByteString/Short/Internal.hs index f81164957..20ea5b4cb 100644 --- a/Data/ByteString/Short/Internal.hs +++ b/Data/ByteString/Short/Internal.hs @@ -31,7 +31,7 @@ module Data.ByteString.Short.Internal ( unpack, -- * Other operations - empty, null, length, index, unsafeIndex, + empty, null, length, index, indexMaybe, (!?), unsafeIndex, -- * Low level operations createFromPtr, copyToPtr, @@ -107,7 +107,8 @@ import Prelude ( Eq(..), Ord(..), Ordering(..), Read(..), Show(..) , String, userError , Bool(..), (&&), otherwise , (+), (-), fromIntegral - , return ) + , return + , Maybe(..) ) -- | A compact representation of a 'Word8' vector. @@ -215,6 +216,24 @@ index sbs i | i >= 0 && i < length sbs = unsafeIndex sbs i | otherwise = indexError sbs i +-- | /O(1)/ 'ShortByteString' index, starting from 0, that returns 'Just' if: +-- +-- > 0 <= n < length bs +-- +-- @since 0.10.10.0 +indexMaybe :: ShortByteString -> Int -> Maybe Word8 +indexMaybe sbs i + | i >= 0 && i < length sbs = Just $ unsafeIndex sbs i + | otherwise = Nothing + +-- | /O(1)/ 'ShortByteString' index, starting from 0, that returns 'Just' if: +-- +-- > 0 <= n < length bs +-- +-- @since 0.10.10.0 +(!?) :: ShortByteString -> Int -> Maybe Word8 +(!?) = indexMaybe + unsafeIndex :: ShortByteString -> Int -> Word8 unsafeIndex sbs = indexWord8Array (asBA sbs) From 4ddbfedebc4fe5aa88087606d2ae079292989a8d Mon Sep 17 00:00:00 2001 From: FintanH Date: Sat, 16 May 2020 15:55:49 +0100 Subject: [PATCH 08/11] Update version in docs and update Changelog --- Changelog.md | 2 +- Data/ByteString.hs | 4 ++-- Data/ByteString/Char8.hs | 4 ++-- Data/ByteString/Lazy.hs | 4 ++-- Data/ByteString/Lazy/Char8.hs | 4 ++-- Data/ByteString/Short/Internal.hs | 4 ++-- 6 files changed, 11 insertions(+), 11 deletions(-) diff --git a/Changelog.md b/Changelog.md index 3ce85f350..e708fb61e 100644 --- a/Changelog.md +++ b/Changelog.md @@ -9,7 +9,7 @@ * [Add `IsList` instances for strict and lazy `ByteString` and for `ShortByteString`](https://github.com/haskell/bytestring/pull/219) * [Add `createUpToN'` and `unsafeCreateUpToN'` to `Data.ByteString.Internal`](https://github.com/haskell/bytestring/pull/245) * [Add `boundedPrim` to `Data.ByteString.Builder.Prim.Internal` and deprecate `boudedPrim`](https://github.com/haskell/bytestring/pull/246) - * Add `indexMaybe` for indexing that returns `Maybe` + * Add `indexMaybe` and synonym `(!?)` for indexing that returns `Maybe` * [Deprecate the `Data.ByteString.Lazy.Builder` and `Data.ByteString.Lazy.Builder.{ASCII,Extras}` modules](https://github.com/haskell/bytestring/pull/250) * [Fix documented complexity of `Data.ByteString.Lazy.length`](https://github.com/haskell/bytestring/pull/255) * [Assorted documentation fixes](https://github.com/haskell/bytestring/pull/248) diff --git a/Data/ByteString.hs b/Data/ByteString.hs index a6c1b8bfb..0d24be2ea 100644 --- a/Data/ByteString.hs +++ b/Data/ByteString.hs @@ -1103,7 +1103,7 @@ index ps n -- -- > 0 <= n < length bs -- --- @since 0.10.10.0 +-- @since 0.10.10.1 indexMaybe :: ByteString -> Int -> Maybe Word8 indexMaybe ps n | n < 0 = Nothing @@ -1115,7 +1115,7 @@ indexMaybe ps n -- -- > 0 <= n < length bs -- --- @since 0.10.10.0 +-- @since 0.10.10.1 (!?) :: ByteString -> Int -> Maybe Word8 (!?) = indexMaybe {-# INLINE (!?) #-} diff --git a/Data/ByteString/Char8.hs b/Data/ByteString/Char8.hs index 466468c11..2dd3d4eca 100644 --- a/Data/ByteString/Char8.hs +++ b/Data/ByteString/Char8.hs @@ -650,7 +650,7 @@ index = (w2c .) . B.index -- -- > 0 <= n < length bs -- --- @since 0.10.10.0 +-- @since 0.10.10.1 indexMaybe :: ByteString -> Int -> Maybe Char indexMaybe = ((fmap w2c) .) . B.indexMaybe {-# INLINE indexMaybe #-} @@ -659,7 +659,7 @@ indexMaybe = ((fmap w2c) .) . B.indexMaybe -- -- > 0 <= n < length bs -- --- @since 0.10.10.0 +-- @since 0.10.10.1 (!?) :: ByteString -> Int -> Maybe Char (!?) = indexMaybe {-# INLINE (!?) #-} diff --git a/Data/ByteString/Lazy.hs b/Data/ByteString/Lazy.hs index a434820a9..d5d62df90 100644 --- a/Data/ByteString/Lazy.hs +++ b/Data/ByteString/Lazy.hs @@ -901,7 +901,7 @@ index cs0 i = index' cs0 i -- -- > 0 <= n < length bs -- --- @since 0.10.10.0 +-- @since 0.10.10.1 indexMaybe :: ByteString -> Int64 -> Maybe Word8 indexMaybe _ i | i < 0 = Nothing indexMaybe cs0 i = index' cs0 i @@ -915,7 +915,7 @@ indexMaybe cs0 i = index' cs0 i -- -- > 0 <= n < length bs -- --- @since 0.10.10.0 +-- @since 0.10.10.1 (!?) :: ByteString -> Int64 -> Maybe Word8 (!?) = indexMaybe {-# INLINE (!?) #-} diff --git a/Data/ByteString/Lazy/Char8.hs b/Data/ByteString/Lazy/Char8.hs index a41a3902d..48f668ebe 100644 --- a/Data/ByteString/Lazy/Char8.hs +++ b/Data/ByteString/Lazy/Char8.hs @@ -533,7 +533,7 @@ index = (w2c .) . L.index -- -- > 0 <= n < length bs -- --- @since 0.10.10.0 +-- @since 0.10.10.1 indexMaybe :: ByteString -> Int64 -> Maybe Char indexMaybe = ((fmap w2c) .) . L.indexMaybe {-# INLINE indexMaybe #-} @@ -542,7 +542,7 @@ indexMaybe = ((fmap w2c) .) . L.indexMaybe -- -- > 0 <= n < length bs -- --- @since 0.10.10.0 +-- @since 0.10.10.1 (!?) :: ByteString -> Int64 -> Maybe Char (!?) = indexMaybe {-# INLINE (!?) #-} diff --git a/Data/ByteString/Short/Internal.hs b/Data/ByteString/Short/Internal.hs index 20ea5b4cb..46d2b6443 100644 --- a/Data/ByteString/Short/Internal.hs +++ b/Data/ByteString/Short/Internal.hs @@ -220,7 +220,7 @@ index sbs i -- -- > 0 <= n < length bs -- --- @since 0.10.10.0 +-- @since 0.10.10.1 indexMaybe :: ShortByteString -> Int -> Maybe Word8 indexMaybe sbs i | i >= 0 && i < length sbs = Just $ unsafeIndex sbs i @@ -230,7 +230,7 @@ indexMaybe sbs i -- -- > 0 <= n < length bs -- --- @since 0.10.10.0 +-- @since 0.10.10.1 (!?) :: ShortByteString -> Int -> Maybe Word8 (!?) = indexMaybe From 2cd5ce986c310225fb49e5bd41e152b3437c1642 Mon Sep 17 00:00:00 2001 From: Cole Miller Date: Fri, 21 Aug 2020 19:01:35 -0400 Subject: [PATCH 09/11] Implement requested changes from #146 review --- Changelog.md | 6 +++++- Data/ByteString.hs | 4 ++-- Data/ByteString/Char8.hs | 6 +++--- Data/ByteString/Lazy.hs | 4 ++-- Data/ByteString/Lazy/Char8.hs | 6 +++--- Data/ByteString/Short/Internal.hs | 4 ++-- 6 files changed, 17 insertions(+), 13 deletions(-) diff --git a/Changelog.md b/Changelog.md index e708fb61e..2f0260257 100644 --- a/Changelog.md +++ b/Changelog.md @@ -1,3 +1,8 @@ +[0.11.0.0] — + * [Add `indexMaybe` and synonym `(!?)` for indexing that returns `Maybe`](https://github.com/haskell/bytestring/pull/261) + +[0.11.0.0]: https://github.com/haskell/bytestring/compare/0.10.12.0...0.11.0.0 + [0.10.12.0] – August 2020 * **Note:** There are several breaking changes planned to be included in v0.11. @@ -9,7 +14,6 @@ * [Add `IsList` instances for strict and lazy `ByteString` and for `ShortByteString`](https://github.com/haskell/bytestring/pull/219) * [Add `createUpToN'` and `unsafeCreateUpToN'` to `Data.ByteString.Internal`](https://github.com/haskell/bytestring/pull/245) * [Add `boundedPrim` to `Data.ByteString.Builder.Prim.Internal` and deprecate `boudedPrim`](https://github.com/haskell/bytestring/pull/246) - * Add `indexMaybe` and synonym `(!?)` for indexing that returns `Maybe` * [Deprecate the `Data.ByteString.Lazy.Builder` and `Data.ByteString.Lazy.Builder.{ASCII,Extras}` modules](https://github.com/haskell/bytestring/pull/250) * [Fix documented complexity of `Data.ByteString.Lazy.length`](https://github.com/haskell/bytestring/pull/255) * [Assorted documentation fixes](https://github.com/haskell/bytestring/pull/248) diff --git a/Data/ByteString.hs b/Data/ByteString.hs index 0d24be2ea..a70d08625 100644 --- a/Data/ByteString.hs +++ b/Data/ByteString.hs @@ -1103,7 +1103,7 @@ index ps n -- -- > 0 <= n < length bs -- --- @since 0.10.10.1 +-- @since 0.11.0.0 indexMaybe :: ByteString -> Int -> Maybe Word8 indexMaybe ps n | n < 0 = Nothing @@ -1115,7 +1115,7 @@ indexMaybe ps n -- -- > 0 <= n < length bs -- --- @since 0.10.10.1 +-- @since 0.11.0.0 (!?) :: ByteString -> Int -> Maybe Word8 (!?) = indexMaybe {-# INLINE (!?) #-} diff --git a/Data/ByteString/Char8.hs b/Data/ByteString/Char8.hs index 2dd3d4eca..9b099d550 100644 --- a/Data/ByteString/Char8.hs +++ b/Data/ByteString/Char8.hs @@ -650,16 +650,16 @@ index = (w2c .) . B.index -- -- > 0 <= n < length bs -- --- @since 0.10.10.1 +-- @since 0.11.0.0 indexMaybe :: ByteString -> Int -> Maybe Char -indexMaybe = ((fmap w2c) .) . B.indexMaybe +indexMaybe = (fmap w2c .) . B.indexMaybe {-# INLINE indexMaybe #-} -- | /O(1)/ 'ByteString' index, starting from 0, that returns 'Just' if: -- -- > 0 <= n < length bs -- --- @since 0.10.10.1 +-- @since 0.11.0.0 (!?) :: ByteString -> Int -> Maybe Char (!?) = indexMaybe {-# INLINE (!?) #-} diff --git a/Data/ByteString/Lazy.hs b/Data/ByteString/Lazy.hs index d5d62df90..ea92b0b45 100644 --- a/Data/ByteString/Lazy.hs +++ b/Data/ByteString/Lazy.hs @@ -901,7 +901,7 @@ index cs0 i = index' cs0 i -- -- > 0 <= n < length bs -- --- @since 0.10.10.1 +-- @since 0.11.0.0 indexMaybe :: ByteString -> Int64 -> Maybe Word8 indexMaybe _ i | i < 0 = Nothing indexMaybe cs0 i = index' cs0 i @@ -915,7 +915,7 @@ indexMaybe cs0 i = index' cs0 i -- -- > 0 <= n < length bs -- --- @since 0.10.10.1 +-- @since 0.11.0.0 (!?) :: ByteString -> Int64 -> Maybe Word8 (!?) = indexMaybe {-# INLINE (!?) #-} diff --git a/Data/ByteString/Lazy/Char8.hs b/Data/ByteString/Lazy/Char8.hs index 48f668ebe..486c3aca8 100644 --- a/Data/ByteString/Lazy/Char8.hs +++ b/Data/ByteString/Lazy/Char8.hs @@ -533,16 +533,16 @@ index = (w2c .) . L.index -- -- > 0 <= n < length bs -- --- @since 0.10.10.1 +-- @since 0.11.0.0 indexMaybe :: ByteString -> Int64 -> Maybe Char -indexMaybe = ((fmap w2c) .) . L.indexMaybe +indexMaybe = (fmap w2c .) . L.indexMaybe {-# INLINE indexMaybe #-} -- | /O(1)/ 'ByteString' index, starting from 0, that returns 'Just' if: -- -- > 0 <= n < length bs -- --- @since 0.10.10.1 +-- @since 0.11.0.0 (!?) :: ByteString -> Int64 -> Maybe Char (!?) = indexMaybe {-# INLINE (!?) #-} diff --git a/Data/ByteString/Short/Internal.hs b/Data/ByteString/Short/Internal.hs index 46d2b6443..11264f1fb 100644 --- a/Data/ByteString/Short/Internal.hs +++ b/Data/ByteString/Short/Internal.hs @@ -220,7 +220,7 @@ index sbs i -- -- > 0 <= n < length bs -- --- @since 0.10.10.1 +-- @since 0.11.0.0 indexMaybe :: ShortByteString -> Int -> Maybe Word8 indexMaybe sbs i | i >= 0 && i < length sbs = Just $ unsafeIndex sbs i @@ -230,7 +230,7 @@ indexMaybe sbs i -- -- > 0 <= n < length bs -- --- @since 0.10.10.1 +-- @since 0.11.0.0 (!?) :: ShortByteString -> Int -> Maybe Word8 (!?) = indexMaybe From 41bbcf1ec7d940ffc9a6cef97b25fe9caf177c68 Mon Sep 17 00:00:00 2001 From: Cole Miller Date: Fri, 21 Aug 2020 19:19:33 -0400 Subject: [PATCH 10/11] Use strict application in Just branches of indexMaybe --- Data/ByteString.hs | 2 +- Data/ByteString/Lazy.hs | 2 +- Data/ByteString/Short/Internal.hs | 4 ++-- 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/Data/ByteString.hs b/Data/ByteString.hs index a70d08625..d0ef4cb84 100644 --- a/Data/ByteString.hs +++ b/Data/ByteString.hs @@ -1108,7 +1108,7 @@ indexMaybe :: ByteString -> Int -> Maybe Word8 indexMaybe ps n | n < 0 = Nothing | n >= length ps = Nothing - | otherwise = Just $ ps `unsafeIndex` n + | otherwise = Just $! ps `unsafeIndex` n {-# INLINE indexMaybe #-} -- | /O(1)/ 'ByteString' index, starting from 0, that returns 'Just' if: diff --git a/Data/ByteString/Lazy.hs b/Data/ByteString/Lazy.hs index ea92b0b45..959898e1c 100644 --- a/Data/ByteString/Lazy.hs +++ b/Data/ByteString/Lazy.hs @@ -909,7 +909,7 @@ indexMaybe cs0 i = index' cs0 i index' (Chunk c cs) n | n >= fromIntegral (S.length c) = index' cs (n - fromIntegral (S.length c)) - | otherwise = Just $ S.unsafeIndex c (fromIntegral n) + | otherwise = Just $! S.unsafeIndex c (fromIntegral n) -- | /O(1)/ 'ByteString' index, starting from 0, that returns 'Just' if: -- diff --git a/Data/ByteString/Short/Internal.hs b/Data/ByteString/Short/Internal.hs index 11264f1fb..689f90859 100644 --- a/Data/ByteString/Short/Internal.hs +++ b/Data/ByteString/Short/Internal.hs @@ -103,7 +103,7 @@ import GHC.ST (ST(ST), runST) import GHC.Word import Prelude ( Eq(..), Ord(..), Ordering(..), Read(..), Show(..) - , ($), error, (++), (.) + , ($), ($!), error, (++), (.) , String, userError , Bool(..), (&&), otherwise , (+), (-), fromIntegral @@ -223,7 +223,7 @@ index sbs i -- @since 0.11.0.0 indexMaybe :: ShortByteString -> Int -> Maybe Word8 indexMaybe sbs i - | i >= 0 && i < length sbs = Just $ unsafeIndex sbs i + | i >= 0 && i < length sbs = Just $! unsafeIndex sbs i | otherwise = Nothing -- | /O(1)/ 'ShortByteString' index, starting from 0, that returns 'Just' if: From 94536940f4fafdab1b07bde85f34b42a8405b108 Mon Sep 17 00:00:00 2001 From: Cole Miller Date: Sat, 22 Aug 2020 09:54:03 -0400 Subject: [PATCH 11/11] Add missing INLINE pragmas --- Data/ByteString/Short/Internal.hs | 2 ++ 1 file changed, 2 insertions(+) diff --git a/Data/ByteString/Short/Internal.hs b/Data/ByteString/Short/Internal.hs index 689f90859..d5c09d6f4 100644 --- a/Data/ByteString/Short/Internal.hs +++ b/Data/ByteString/Short/Internal.hs @@ -225,6 +225,7 @@ indexMaybe :: ShortByteString -> Int -> Maybe Word8 indexMaybe sbs i | i >= 0 && i < length sbs = Just $! unsafeIndex sbs i | otherwise = Nothing +{-# INLINE indexMaybe #-} -- | /O(1)/ 'ShortByteString' index, starting from 0, that returns 'Just' if: -- @@ -233,6 +234,7 @@ indexMaybe sbs i -- @since 0.11.0.0 (!?) :: ShortByteString -> Int -> Maybe Word8 (!?) = indexMaybe +{-# INLINE (!?) #-} unsafeIndex :: ShortByteString -> Int -> Word8 unsafeIndex sbs = indexWord8Array (asBA sbs)