Skip to content

Commit 39eb600

Browse files
committed
Adding alter function, documentation, and tests.
1 parent c3954e9 commit 39eb600

File tree

4 files changed

+36
-1
lines changed

4 files changed

+36
-1
lines changed

Data/HashMap/Base.hs

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,7 @@ module Data.HashMap.Base
2626
, unsafeInsert
2727
, delete
2828
, adjust
29+
, alter
2930

3031
-- * Combine
3132
-- ** Union
@@ -574,6 +575,16 @@ adjust f k0 m0 = go h0 k0 0 m0
574575
| otherwise = t
575576
{-# INLINABLE adjust #-}
576577

578+
-- | /O(log n)/ The expression (@'alter' f k map@) alters the value @x@ at @k@, or
579+
-- absence thereof. @alter@ can be used to insert, delete, or update a value in a
580+
-- map. In short : @'lookup' k ('alter' f k m) = f ('lookup' k m)@.
581+
alter :: (Eq k, Hashable k) => (Maybe v -> Maybe v) -> k -> HashMap k v -> HashMap k v
582+
alter f k m =
583+
case f (lookup k m) of
584+
Nothing -> delete k m
585+
Just v -> insert k v m
586+
{-# INLINABLE alter #-}
587+
577588
------------------------------------------------------------------------
578589
-- * Combine
579590

Data/HashMap/Lazy.hs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,7 @@ module Data.HashMap.Lazy
4747
, insertWith
4848
, delete
4949
, adjust
50+
, alter
5051

5152
-- * Combine
5253
-- ** Union

Data/HashMap/Strict.hs

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,7 @@ module Data.HashMap.Strict
4747
, insertWith
4848
, delete
4949
, adjust
50+
, alter
5051

5152
-- * Combine
5253
-- ** Union
@@ -92,7 +93,7 @@ import Prelude hiding (map)
9293
import qualified Data.HashMap.Array as A
9394
import qualified Data.HashMap.Base as HM
9495
import Data.HashMap.Base hiding (
95-
adjust, fromList, fromListWith, insert, insertWith, intersectionWith,
96+
alter, adjust, fromList, fromListWith, insert, insertWith, intersectionWith,
9697
map, mapWithKey, singleton, unionWith)
9798
import Data.HashMap.Unsafe (runST)
9899

@@ -227,6 +228,16 @@ adjust f k0 m0 = go h0 k0 0 m0
227228
| otherwise = t
228229
{-# INLINABLE adjust #-}
229230

231+
-- | /O(log n)/ The expression (@'alter' f k map@) alters the value @x@ at @k@, or
232+
-- absence thereof. @alter@ can be used to insert, delete, or update a value in a
233+
-- map. In short : @'lookup' k ('alter' f k m) = f ('lookup' k m)@.
234+
alter :: (Eq k, Hashable k) => (Maybe v -> Maybe v) -> k -> HashMap k v -> HashMap k v
235+
alter f k m =
236+
case f (HM.lookup k m) of
237+
Nothing -> delete k m
238+
Just v -> insert k v m
239+
{-# INLINABLE alter #-}
240+
230241
------------------------------------------------------------------------
231242
-- * Combine
232243

tests/HashMapProperties.hs

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -98,6 +98,15 @@ pInsertWith k = M.insertWith (+) k 1 `eq_` HM.insertWith (+) k 1
9898
pAdjust :: Key -> [(Key, Int)] -> Bool
9999
pAdjust k = M.adjust succ k `eq_` HM.adjust succ k
100100

101+
pAlterAdjust :: Key -> [(Key, Int)] -> Bool
102+
pAlterAdjust k = M.alter (fmap succ) k `eq_` HM.alter (fmap succ) k
103+
104+
pAlterInsert :: Key -> [(Key, Int)] -> Bool
105+
pAlterInsert k = M.alter (const $ Just 3) k `eq_` HM.alter (const $ Just 3) k
106+
107+
pAlterDelete :: Key -> [(Key, Int)] -> Bool
108+
pAlterDelete k = M.alter (const Nothing) k `eq_` HM.alter (const Nothing) k
109+
101110
------------------------------------------------------------------------
102111
-- ** Combine
103112

@@ -209,6 +218,9 @@ tests =
209218
, testProperty "deleteCollision" pDeleteCollision
210219
, testProperty "insertWith" pInsertWith
211220
, testProperty "adjust" pAdjust
221+
, testProperty "alterAdjust" pAlterAdjust
222+
, testProperty "alterInsert" pAlterInsert
223+
, testProperty "alterDelete" pAlterDelete
212224
]
213225
-- Combine
214226
, testProperty "union" pUnion

0 commit comments

Comments
 (0)