diff --git a/containers/src/Data/IntMap/Internal.hs b/containers/src/Data/IntMap/Internal.hs index 6cd047625..d0d345e48 100644 --- a/containers/src/Data/IntMap/Internal.hs +++ b/containers/src/Data/IntMap/Internal.hs @@ -364,6 +364,9 @@ import Text.Read #endif import qualified Control.Category as Category +#if __GLASGOW_HASKELL__ >= 800 +import GHC.Stack (HasCallStack) +#endif {-------------------------------------------------------------------- Types @@ -429,8 +432,20 @@ deriving instance Lift a => Lift (IntMap a) -- > fromList [(5,'a'), (3,'b')] ! 1 Error: element not in the map -- > fromList [(5,'a'), (3,'b')] ! 5 == 'a' +#if __GLASGOW_HASKELL__ >= 800 +(!) :: HasCallStack => IntMap a -> Key -> a +#else (!) :: IntMap a -> Key -> a -(!) m k = find k m +#endif +(!) m0 !k = go m0 + where + go (Bin p l r) | left k p = go l + | otherwise = go r + go (Tip kx x) | k == kx = x + | otherwise = not_found + go Nil = not_found + + not_found = error ("IntMap.!: key " ++ show k ++ " is not an element of the map") -- | \(O(\min(n,W))\). Find the value at a key. -- Returns 'Nothing' when the element can not be found. @@ -648,18 +663,6 @@ lookup !k = go | otherwise = Nothing go Nil = Nothing --- See Note: Local 'go' functions and capturing] -find :: Key -> IntMap a -> a -find !k = go - where - go (Bin p l r) | left k p = go l - | otherwise = go r - go (Tip kx x) | k == kx = x - | otherwise = not_found - go Nil = not_found - - not_found = error ("IntMap.!: key " ++ show k ++ " is not an element of the map") - -- | \(O(\min(n,W))\). The expression @('findWithDefault' def k map)@ -- returns the value at key @k@ or returns @def@ when the key is not an -- element of the map. @@ -2351,7 +2354,11 @@ minView t = fmap (\((_, x), t') -> (x, t')) (minViewWithKey t) -- Calls 'error' if the map is empty. -- -- __Note__: This function is partial. Prefer 'maxViewWithKey'. +#if __GLASGOW_HASKELL__ >= 800 +deleteFindMax :: HasCallStack => IntMap a -> ((Key, a), IntMap a) +#else deleteFindMax :: IntMap a -> ((Key, a), IntMap a) +#endif deleteFindMax = fromMaybe (error "deleteFindMax: empty map has no maximal element") . maxViewWithKey -- | \(O(\min(n,W))\). Delete and find the minimal element. @@ -2359,7 +2366,11 @@ deleteFindMax = fromMaybe (error "deleteFindMax: empty map has no maximal elemen -- Calls 'error' if the map is empty. -- -- __Note__: This function is partial. Prefer 'minViewWithKey'. +#if __GLASGOW_HASKELL__ >= 800 +deleteFindMin :: HasCallStack => IntMap a -> ((Key, a), IntMap a) +#else deleteFindMin :: IntMap a -> ((Key, a), IntMap a) +#endif deleteFindMin = fromMaybe (error "deleteFindMin: empty map has no minimal element") . minViewWithKey -- The KeyValue type is used when returning a key-value pair and helps with @@ -2394,7 +2405,11 @@ lookupMin (Bin p l r) = -- | \(O(\min(n,W))\). The minimal key of the map. Calls 'error' if the map is empty. -- -- __Note__: This function is partial. Prefer 'lookupMin'. +#if __GLASGOW_HASKELL__ >= 800 +findMin :: HasCallStack => IntMap a -> (Key, a) +#else findMin :: IntMap a -> (Key, a) +#endif findMin t | Just r <- lookupMin t = r | otherwise = error "findMin: empty map has no minimal element" @@ -2415,7 +2430,11 @@ lookupMax (Bin p l r) = -- | \(O(\min(n,W))\). The maximal key of the map. Calls 'error' if the map is empty. -- -- __Note__: This function is partial. Prefer 'lookupMax'. +#if __GLASGOW_HASKELL__ >= 800 +findMax :: HasCallStack => IntMap a -> (Key, a) +#else findMax :: IntMap a -> (Key, a) +#endif findMax t | Just r <- lookupMax t = r | otherwise = error "findMax: empty map has no maximal element" diff --git a/containers/src/Data/IntSet/Internal.hs b/containers/src/Data/IntSet/Internal.hs index 9008244e3..2b49f8ac7 100644 --- a/containers/src/Data/IntSet/Internal.hs +++ b/containers/src/Data/IntSet/Internal.hs @@ -234,6 +234,10 @@ import Language.Haskell.TH () import qualified Data.Foldable as Foldable import Data.Functor.Identity (Identity(..)) +#if __GLASGOW_HASKELL__ >= 800 +import GHC.Stack (HasCallStack) +#endif + infixl 9 \\{-This comment teaches CPP correct behaviour -} {-------------------------------------------------------------------- @@ -1103,7 +1107,11 @@ minView t = -- Calls 'error' if the set is empty. -- -- __Note__: This function is partial. Prefer 'minView'. +#if __GLASGOW_HASKELL__ >= 800 +deleteFindMin :: HasCallStack => IntSet -> (Key, IntSet) +#else deleteFindMin :: IntSet -> (Key, IntSet) +#endif deleteFindMin = fromMaybe (error "deleteFindMin: empty set has no minimal element") . minView -- | \(O(\min(n,W))\). Delete and find the maximal element. @@ -1111,7 +1119,11 @@ deleteFindMin = fromMaybe (error "deleteFindMin: empty set has no minimal elemen -- Calls 'error' if the set is empty. -- -- __Note__: This function is partial. Prefer 'maxView'. +#if __GLASGOW_HASKELL__ >= 800 +deleteFindMax :: HasCallStack => IntSet -> (Key, IntSet) +#else deleteFindMax :: IntSet -> (Key, IntSet) +#endif deleteFindMax = fromMaybe (error "deleteFindMax: empty set has no maximal element") . maxView lookupMinSure :: IntSet -> Key @@ -1133,7 +1145,11 @@ lookupMin (Bin p l r) = Just $! lookupMinSure (if signBranch p then r else l) -- is empty. -- -- __Note__: This function is partial. Prefer 'lookupMin'. +#if __GLASGOW_HASKELL__ >= 800 +findMin :: HasCallStack => IntSet -> Key +#else findMin :: IntSet -> Key +#endif findMin t | Just r <- lookupMin t = r | otherwise = error "findMin: empty set has no minimal element" @@ -1157,7 +1173,11 @@ lookupMax (Bin p l r) = Just $! lookupMaxSure (if signBranch p then l else r) -- is empty. -- -- __Note__: This function is partial. Prefer 'lookupMax'. +#if __GLASGOW_HASKELL__ >= 800 +findMax :: HasCallStack => IntSet -> Key +#else findMax :: IntSet -> Key +#endif findMax t | Just r <- lookupMax t = r | otherwise = error "findMax: empty set has no maximal element" diff --git a/containers/src/Data/Map/Internal.hs b/containers/src/Data/Map/Internal.hs index 40181416f..91a44d8e9 100644 --- a/containers/src/Data/Map/Internal.hs +++ b/containers/src/Data/Map/Internal.hs @@ -426,6 +426,9 @@ import Data.Coerce import Text.Read hiding (lift) #endif import qualified Control.Category as Category +#if __GLASGOW_HASKELL__ >= 800 +import GHC.Stack (HasCallStack) +#endif {-------------------------------------------------------------------- Operators @@ -440,8 +443,18 @@ infixl 9 !,!?,\\ -- -- > fromList [(5,'a'), (3,'b')] ! 1 Error: element not in the map -- > fromList [(5,'a'), (3,'b')] ! 5 == 'a' +#if __GLASGOW_HASKELL__ >= 800 +(!) :: (HasCallStack, Ord k) => Map k a -> k -> a +#else (!) :: Ord k => Map k a -> k -> a -(!) m k = find k m +#endif +(!) m !k = go m + where + go Tip = error "Map.!: given key is not an element in the map" + go (Bin _ kx x l r) = case compare k kx of + LT -> go l + GT -> go r + EQ -> x #if __GLASGOW_HASKELL__ {-# INLINE (!) #-} #endif @@ -626,20 +639,6 @@ notMember k m = not $ member k m {-# INLINE notMember #-} #endif -find :: Ord k => k -> Map k a -> a -find = go - where - go !_ Tip = error "Map.!: given key is not an element in the map" - go k (Bin _ kx x l r) = case compare k kx of - LT -> go k l - GT -> go k r - EQ -> x -#if __GLASGOW_HASKELL__ -{-# INLINABLE find #-} -#else -{-# INLINE find #-} -#endif - -- | \(O(\log n)\). The expression @('findWithDefault' def k map)@ returns -- the value at key @k@ or returns default value @def@ -- when the key is not in the map. @@ -1484,7 +1483,11 @@ alterFYoneda = go -- > findIndex 6 (fromList [(5,"a"), (3,"b")]) Error: element is not in the map -- See Note: Type of local 'go' function +#if __GLASGOW_HASKELL__ >= 800 +findIndex :: (HasCallStack, Ord k) => k -> Map k a -> Int +#else findIndex :: Ord k => k -> Map k a -> Int +#endif findIndex = go 0 where go :: Ord k => Int -> k -> Map k a -> Int @@ -1530,6 +1533,18 @@ lookupIndex = go 0 -- > elemAt 1 (fromList [(5,"a"), (3,"b")]) == (5, "a") -- > elemAt 2 (fromList [(5,"a"), (3,"b")]) Error: index out of range +#if __GLASGOW_HASKELL__ >= 800 +elemAt :: HasCallStack => Int -> Map k a -> (k,a) +elemAt = go where + go !_ Tip = error "Map.elemAt: index out of range" + go i (Bin _ kx x l r) + = case compare i sizeL of + LT -> elemAt i l + GT -> elemAt (i-sizeL-1) r + EQ -> (kx,x) + where + sizeL = size l +#else elemAt :: Int -> Map k a -> (k,a) elemAt !_ Tip = error "Map.elemAt: index out of range" elemAt i (Bin _ kx x l r) @@ -1539,6 +1554,7 @@ elemAt i (Bin _ kx x l r) EQ -> (kx,x) where sizeL = size l +#endif -- | \(O(\log n)\). Take a given number of entries in key order, beginning -- with the smallest keys. @@ -1621,6 +1637,21 @@ splitAt i0 m0 -- > updateAt (\_ _ -> Nothing) 2 (fromList [(5,"a"), (3,"b")]) Error: index out of range -- > updateAt (\_ _ -> Nothing) (-1) (fromList [(5,"a"), (3,"b")]) Error: index out of range +#if __GLASGOW_HASKELL__ >= 800 +updateAt :: HasCallStack => (k -> a -> Maybe a) -> Int -> Map k a -> Map k a +updateAt = go where + go f !i t = + case t of + Tip -> error "Map.updateAt: index out of range" + Bin sx kx x l r -> case compare i sizeL of + LT -> balanceR kx x (go f i l) r + GT -> balanceL kx x l (go f (i-sizeL-1) r) + EQ -> case f kx x of + Just x' -> Bin sx kx x' l r + Nothing -> glue l r + where + sizeL = size l +#else updateAt :: (k -> a -> Maybe a) -> Int -> Map k a -> Map k a updateAt f !i t = case t of @@ -1633,6 +1664,7 @@ updateAt f !i t = Nothing -> glue l r where sizeL = size l +#endif -- | \(O(\log n)\). Delete the element at /index/, i.e. by its zero-based index in -- the sequence sorted by keys. If the /index/ is out of range (less than zero, @@ -1645,6 +1677,19 @@ updateAt f !i t = -- > deleteAt 2 (fromList [(5,"a"), (3,"b")]) Error: index out of range -- > deleteAt (-1) (fromList [(5,"a"), (3,"b")]) Error: index out of range +#if __GLASGOW_HASKELL__ >= 800 +deleteAt :: HasCallStack => Int -> Map k a -> Map k a +deleteAt = go where + go !i t = + case t of + Tip -> error "Map.deleteAt: index out of range" + Bin _ kx x l r -> case compare i sizeL of + LT -> balanceR kx x (go i l) r + GT -> balanceL kx x l (go (i-sizeL-1) r) + EQ -> glue l r + where + sizeL = size l +#else deleteAt :: Int -> Map k a -> Map k a deleteAt !i t = case t of @@ -1655,6 +1700,7 @@ deleteAt !i t = EQ -> glue l r where sizeL = size l +#endif {-------------------------------------------------------------------- @@ -1702,7 +1748,11 @@ lookupMin (Bin _ k x l _) = Just $! kvToTuple (lookupMinSure k x l) -- > findMin (fromList [(5,"a"), (3,"b")]) == (3,"b") -- > findMin empty Error: empty map has no minimal element +#if __GLASGOW_HASKELL__ >= 800 +findMin :: HasCallStack => Map k a -> (k,a) +#else findMin :: Map k a -> (k,a) +#endif findMin t | Just r <- lookupMin t = r | otherwise = error "Map.findMin: empty map has no minimal element" @@ -1730,7 +1780,11 @@ lookupMax (Bin _ k x _ r) = Just $! kvToTuple (lookupMaxSure k x r) -- > findMax (fromList [(5,"a"), (3,"b")]) == (5,"a") -- > findMax empty Error: empty map has no maximal element +#if __GLASGOW_HASKELL__ >= 800 +findMax :: HasCallStack => Map k a -> (k,a) +#else findMax :: Map k a -> (k,a) +#endif findMax t | Just r <- lookupMax t = r | otherwise = error "Map.findMax: empty map has no maximal element" @@ -4182,7 +4236,11 @@ maxViewSure !k x !l r = case r of -- Calls 'error' if the map is empty. -- -- __Note__: This function is partial. Prefer 'minViewWithKey'. +#if __GLASGOW_HASKELL__ >= 800 +deleteFindMin :: HasCallStack => Map k a -> ((k,a),Map k a) +#else deleteFindMin :: Map k a -> ((k,a),Map k a) +#endif deleteFindMin t = case minViewWithKey t of Nothing -> (error "Map.deleteFindMin: can not return the minimal element of an empty map", Tip) Just res -> res @@ -4192,7 +4250,11 @@ deleteFindMin t = case minViewWithKey t of -- Calls 'error' if the map is empty. -- -- __Note__: This function is partial. Prefer 'maxViewWithKey'. +#if __GLASGOW_HASKELL__ >= 800 +deleteFindMax :: HasCallStack => Map k a -> ((k,a),Map k a) +#else deleteFindMax :: Map k a -> ((k,a),Map k a) +#endif deleteFindMax t = case maxViewWithKey t of Nothing -> (error "Map.deleteFindMax: can not return the maximal element of an empty map", Tip) Just res -> res diff --git a/containers/src/Data/Map/Strict/Internal.hs b/containers/src/Data/Map/Strict/Internal.hs index d70977e38..e066a2904 100644 --- a/containers/src/Data/Map/Strict/Internal.hs +++ b/containers/src/Data/Map/Strict/Internal.hs @@ -424,6 +424,10 @@ import Data.Coerce import Data.Functor.Identity (Identity (..)) #endif +#if __GLASGOW_HASKELL__ >= 800 +import GHC.Stack (HasCallStack) +#endif + import qualified Data.Foldable as Foldable -- [Note: Pointer equality for sharing] @@ -869,6 +873,21 @@ atKeyIdentity k f t = Identity $ atKeyPlain Strict k (coerce f) t -- > updateAt (\_ _ -> Nothing) 2 (fromList [(5,"a"), (3,"b")]) Error: index out of range -- > updateAt (\_ _ -> Nothing) (-1) (fromList [(5,"a"), (3,"b")]) Error: index out of range +#if __GLASGOW_HASKELL__ >= 800 +updateAt :: HasCallStack => (k -> a -> Maybe a) -> Int -> Map k a -> Map k a +updateAt = go where + go f i t = i `seq` + case t of + Tip -> error "Map.updateAt: index out of range" + Bin sx kx x l r -> case compare i sizeL of + LT -> balanceR kx x (go f i l) r + GT -> balanceL kx x l (go f (i-sizeL-1) r) + EQ -> case f kx x of + Just x' -> x' `seq` Bin sx kx x' l r + Nothing -> glue l r + where + sizeL = size l +#else updateAt :: (k -> a -> Maybe a) -> Int -> Map k a -> Map k a updateAt f i t = i `seq` case t of @@ -881,6 +900,7 @@ updateAt f i t = i `seq` Nothing -> glue l r where sizeL = size l +#endif {-------------------------------------------------------------------- Minimal, Maximal diff --git a/containers/src/Data/Sequence/Internal.hs b/containers/src/Data/Sequence/Internal.hs index ac9796ab3..11061864e 100644 --- a/containers/src/Data/Sequence/Internal.hs +++ b/containers/src/Data/Sequence/Internal.hs @@ -235,6 +235,10 @@ import Utils.Containers.Internal.StrictPair (StrictPair (..), toPair) import Control.Monad.Zip (MonadZip (..)) import Control.Monad.Fix (MonadFix (..), fix) +#if __GLASGOW_HASKELL__ >= 800 +import GHC.Stack (HasCallStack) +#endif + default () -- We define our own copy here, for Monoid only, even though this @@ -518,7 +522,11 @@ instance MonadFix Seq where -- This is just like the instance for lists, but we can take advantage of -- constant-time length and logarithmic-time indexing to speed things up. -- Using fromFunction, we make this about as lazy as we can. +#if __GLASGOW_HASKELL__ >= 800 +mfixSeq :: HasCallStack => (a -> Seq a) -> Seq a +#else mfixSeq :: (a -> Seq a) -> Seq a +#endif mfixSeq f = fromFunction (length (f err)) (\k -> fix (\xk -> f xk `index` k)) where err = error "mfix for Data.Sequence.Seq applied to strict function" @@ -1764,7 +1772,11 @@ singleton x = Seq (Single (Elem x)) -- Calls 'error' if @n < 0@. -- -- __Note__: This function is partial. +#if __GLASGOW_HASKELL__ >= 800 +replicate :: HasCallStack => Int -> a -> Seq a +#else replicate :: Int -> a -> Seq a +#endif replicate n x | n >= 0 = runIdentity (replicateA n (Identity x)) | otherwise = error "replicate takes a nonnegative integer argument" @@ -1777,7 +1789,11 @@ replicate n x -- __Note__: This function is partial. -- -- > replicateA n x = sequenceA (replicate n x) +#if __GLASGOW_HASKELL__ >= 800 +replicateA :: (HasCallStack, Applicative f) => Int -> f a -> f (Seq a) +#else replicateA :: Applicative f => Int -> f a -> f (Seq a) +#endif replicateA n x | n >= 0 = Seq <$> applicativeTree n 1 (Elem <$> x) | otherwise = error "replicateA takes a nonnegative integer argument" @@ -1786,7 +1802,11 @@ replicateA n x -- | Synonym for 'replicateA'. -- -- This definition exists for backwards compatibility. -replicateM :: Applicative m => Int -> m a -> m (Seq a) +#if __GLASGOW_HASKELL__ >= 800 +replicateM :: (HasCallStack, Applicative m) => Int -> m a -> m (Seq a) +#else +replicateM :: (Applicative m) => Int -> m a -> m (Seq a) +#endif replicateM = replicateA -- | \(O(\log k)\). @'cycleTaking' k xs@ forms a sequence of length @k@ by @@ -1804,7 +1824,11 @@ replicateM = replicateA -- __Note__: This function is partial. -- -- @since 0.5.8 +#if __GLASGOW_HASKELL__ >= 800 +cycleTaking :: HasCallStack => Int -> Seq a -> Seq a +#else cycleTaking :: Int -> Seq a -> Seq a +#endif cycleTaking n !_xs | n <= 0 = empty cycleTaking _n xs | null xs = error "cycleTaking cannot take a positive number of elements from an empty cycle." cycleTaking n xs = cycleNTimes reps xs >< take final xs @@ -2218,7 +2242,11 @@ unfoldl f = unfoldl' empty -- Calls 'error' if @n < 0@. -- -- __Note__: This function is partial. +#if __GLASGOW_HASKELL__ >= 800 +iterateN :: HasCallStack => Int -> (a -> a) -> a -> Seq a +#else iterateN :: Int -> (a -> a) -> a -> Seq a +#endif iterateN n f x | n >= 0 = replicateA n (State (\ y -> (f y, y))) `execState` x | otherwise = error "iterateN takes a nonnegative integer argument" @@ -2401,7 +2429,11 @@ scanl f z0 xs = z0 <| snd (mapAccumL (\ x z -> let x' = f x z in (x', x')) z0 xs -- __Note__: This function is partial. -- -- > scanl1 f (fromList [x1, x2, ...]) = fromList [x1, x1 `f` x2, ...] +#if __GLASGOW_HASKELL__ >= 800 +scanl1 :: HasCallStack => (a -> a -> a) -> Seq a -> Seq a +#else scanl1 :: (a -> a -> a) -> Seq a -> Seq a +#endif scanl1 f xs = case viewl xs of EmptyL -> error "scanl1 takes a nonempty sequence as an argument" x :< xs' -> scanl f x xs' @@ -2415,7 +2447,11 @@ scanr f z0 xs = snd (mapAccumR (\ z x -> let z' = f x z in (z', z')) z0 xs) |> z -- Calls 'error' if the sequence is empty. -- -- __Note__: This function is partial. +#if __GLASGOW_HASKELL__ >= 800 +scanr1 :: HasCallStack => (a -> a -> a) -> Seq a -> Seq a +#else scanr1 :: (a -> a -> a) -> Seq a -> Seq a +#endif scanr1 f xs = case viewr xs of EmptyR -> error "scanr1 takes a nonempty sequence as an argument" xs' :> x -> scanr f x xs' @@ -2435,7 +2471,11 @@ scanr1 f xs = case viewr xs of -- element until the result is forced. It can therefore lead to a space -- leak if the result is stored, unforced, in another structure. To retrieve -- an element immediately without forcing it, use 'lookup' or '(!?)'. +#if __GLASGOW_HASKELL__ >= 800 +index :: HasCallStack => Seq a -> Int -> a +#else index :: Seq a -> Int -> a +#endif index (Seq xs) i -- See note on unsigned arithmetic in splitAt | fromIntegral i < (fromIntegral (size xs) :: Word) = case lookupTree i xs of @@ -3407,7 +3447,11 @@ valid. -- __Note__: This function is partial. -- -- @since 0.5.6.2 +#if __GLASGOW_HASKELL__ >= 800 +fromFunction :: HasCallStack => Int -> (Int -> a) -> Seq a +#else fromFunction :: Int -> (Int -> a) -> Seq a +#endif fromFunction len f | len < 0 = error "Data.Sequence.fromFunction called with negative len" | len == 0 = empty | otherwise = Seq $ create (lift_elem f) 1 0 len @@ -3989,7 +4033,11 @@ splitSuffixN i s pr m (Four a b c d) -- __Note__: This function is partial. -- -- @since 0.5.8 +#if __GLASGOW_HASKELL__ >= 800 +chunksOf :: HasCallStack => Int -> Seq a -> Seq (Seq a) +#else chunksOf :: Int -> Seq a -> Seq (Seq a) +#endif chunksOf n xs | n <= 0 = if null xs then empty diff --git a/containers/src/Data/Set/Internal.hs b/containers/src/Data/Set/Internal.hs index 4682abc8c..08b6fa90a 100644 --- a/containers/src/Data/Set/Internal.hs +++ b/containers/src/Data/Set/Internal.hs @@ -258,6 +258,10 @@ import Language.Haskell.TH () import Data.Coerce (coerce) #endif +#if __GLASGOW_HASKELL__ >= 800 +import GHC.Stack (HasCallStack) +#endif + {-------------------------------------------------------------------- Operators @@ -778,7 +782,11 @@ lookupMin (Bin _ x l _) = Just $! lookupMinSure x l -- empty. -- -- __Note__: This function is partial. Prefer 'lookupMin'. +#if __GLASGOW_HASKELL__ >= 800 +findMin :: HasCallStack => Set a -> a +#else findMin :: Set a -> a +#endif findMin t | Just r <- lookupMin t = r | otherwise = error "Set.findMin: empty set has no minimal element" @@ -801,7 +809,11 @@ lookupMax (Bin _ x _ r) = Just $! lookupMaxSure x r -- empty. -- -- __Note__: This function is partial. Prefer 'lookupMax'. +#if __GLASGOW_HASKELL__ >= 800 +findMax :: HasCallStack => Set a -> a +#else findMax :: Set a -> a +#endif findMax t | Just r <- lookupMax t = r | otherwise = error "Set.findMax: empty set has no maximal element" @@ -1457,7 +1469,11 @@ splitMember x (Bin _ y l r) -- @since 0.5.4 -- See Note: Type of local 'go' function +#if __GLASGOW_HASKELL__ >= 800 +findIndex :: (HasCallStack, Ord a) => a -> Set a -> Int +#else findIndex :: Ord a => a -> Set a -> Int +#endif findIndex = go 0 where go :: Ord a => Int -> a -> Set a -> Int @@ -1507,6 +1523,18 @@ lookupIndex = go 0 -- -- @since 0.5.4 +#if __GLASGOW_HASKELL__ >= 800 +elemAt :: HasCallStack => Int -> Set a -> a +elemAt = go where + go !_ Tip = error "Set.elemAt: index out of range" + go i (Bin _ x l r) + = case compare i sizeL of + LT -> go i l + GT -> go (i-sizeL-1) r + EQ -> x + where + sizeL = size l +#else elemAt :: Int -> Set a -> a elemAt !_ Tip = error "Set.elemAt: index out of range" elemAt i (Bin _ x l r) @@ -1516,6 +1544,7 @@ elemAt i (Bin _ x l r) EQ -> x where sizeL = size l +#endif -- | \(O(\log n)\). Delete the element at /index/, i.e. by its zero-based index in -- the sorted sequence of elements. If the /index/ is out of range (less than zero, @@ -1530,6 +1559,19 @@ elemAt i (Bin _ x l r) -- -- @since 0.5.4 +#if __GLASGOW_HASKELL__ >= 800 +deleteAt :: HasCallStack => Int -> Set a -> Set a +deleteAt = go where + go !i t = + case t of + Tip -> error "Set.deleteAt: index out of range" + Bin _ x l r -> case compare i sizeL of + LT -> balanceR x (go i l) r + GT -> balanceL x l (go (i-sizeL-1) r) + EQ -> glue l r + where + sizeL = size l +#else deleteAt :: Int -> Set a -> Set a deleteAt !i t = case t of @@ -1540,6 +1582,7 @@ deleteAt !i t = EQ -> glue l r where sizeL = size l +#endif -- | \(O(\log n)\). Take a given number of elements in order, beginning -- with the smallest ones. @@ -1828,7 +1871,11 @@ glue l@(Bin sl xl ll lr) r@(Bin sr xr rl rr) -- Calls 'error' if the set is empty. -- -- __Note__: This function is partial. Prefer 'minView'. +#if __GLASGOW_HASKELL__ >= 800 +deleteFindMin :: HasCallStack => Set a -> (a,Set a) +#else deleteFindMin :: Set a -> (a,Set a) +#endif deleteFindMin t | Just r <- minView t = r | otherwise = (error "Set.deleteFindMin: can not return the minimal element of an empty set", Tip) @@ -1838,7 +1885,11 @@ deleteFindMin t -- Calls 'error' if the set is empty. -- -- __Note__: This function is partial. Prefer 'maxView'. +#if __GLASGOW_HASKELL__ >= 800 +deleteFindMax :: HasCallStack => Set a -> (a,Set a) +#else deleteFindMax :: Set a -> (a,Set a) +#endif deleteFindMax t | Just r <- maxView t = r | otherwise = (error "Set.deleteFindMax: can not return the maximal element of an empty set", Tip)