@@ -709,6 +709,50 @@ insertWith f k0 v0 m0 = go h0 k0 v0 0 m0
709
709
| otherwise = go h k x s $ BitmapIndexed (mask hy s) (A. singleton t)
710
710
{-# INLINABLE insertWith #-}
711
711
712
+ -- | /O(log n)/ Associate the value with the key in this map. If
713
+ -- this map previously contained a mapping for the key, the old value
714
+ -- is replaced by the result of applying the given function to the new
715
+ -- and old value. Example:
716
+ --
717
+ -- > insertWithInternal f k v map
718
+ -- > where f new old = new + old
719
+ insertWithInternal :: (Eq k , Hashable k ) => (v -> v -> v ) -> k -> v -> HashMap k v
720
+ -> (Int , HashMap k v )
721
+ insertWithInternal f k0 v0 m0 = go h0 k0 v0 0 m0
722
+ where
723
+ h0 = hash k0
724
+ go ! h ! k x ! _ Empty = (1 , Leaf h (L k x))
725
+ go h k x s (Leaf hy l@ (L ky y))
726
+ | hy == h = if ky == k
727
+ then (0 , Leaf h (L k (f x y)))
728
+ else (1 , collision h l (L k x))
729
+ | otherwise = (0 , runST (two s h k x hy ky y))
730
+ go h k x s (BitmapIndexed b ary)
731
+ | b .&. m == 0 =
732
+ let ary' = A. insert ary i $! Leaf h (L k x)
733
+ in (1 , bitmapIndexedOrFull (b .|. m) ary')
734
+ | otherwise =
735
+ let st = A. index ary i
736
+ (sz, st') = go h k x (s+ bitsPerSubkey) st
737
+ ary' = A. update ary i $! st'
738
+ in (sz, BitmapIndexed b ary')
739
+ where m = mask h s
740
+ i = sparseIndex b m
741
+ go h k x s (Full ary) =
742
+ let st = A. index ary i
743
+ (sz, st') = go h k x (s+ bitsPerSubkey) st
744
+ ary' = update16 ary i $! st'
745
+ in (sz, Full ary')
746
+ where i = index h s
747
+ go h k x s t@ (Collision hy v)
748
+ | h == hy =
749
+ let ! start = A. length v
750
+ ! newV = updateOrSnocWith const k x v
751
+ ! end = A. length newV
752
+ in (end - start, Collision h newV)
753
+ | otherwise = go h k x s $ BitmapIndexed (mask hy s) (A. singleton t)
754
+ {-# INLINABLE insertWithInternal #-}
755
+
712
756
-- | In-place update version of insertWith
713
757
unsafeInsertWith :: forall k v . (Eq k , Hashable k )
714
758
=> (v -> v -> v ) -> k -> v -> HashMap k v
0 commit comments