@@ -28,21 +28,63 @@ module Data.StrMap
28
28
foldMap ,
29
29
foldM ,
30
30
foldMaybe ,
31
- all
31
+ all ,
32
+
33
+ thawST ,
34
+ freezeST ,
35
+ runST
32
36
) where
33
37
34
38
import qualified Prelude as P
35
39
40
+ import Control.Monad.Eff (Eff (), runPure )
41
+ import qualified Control.Monad.ST as ST
36
42
import qualified Data.Array as A
37
43
import Data.Maybe
38
44
import Data.Function
39
45
import Data.Tuple
40
- import Data.Foldable (Foldable , foldl , foldr )
46
+ import Data.Foldable (Foldable , foldl , foldr , for_ )
41
47
import Data.Monoid
42
48
import Data.Monoid.All
49
+ import qualified Data.StrMap.ST as SM
43
50
44
51
foreign import data StrMap :: * -> *
45
52
53
+ foreign import _copy " " "
54
+ function _copy(m) {
55
+ var r = {};
56
+ for (var k in m)
57
+ r[k] = m[k]
58
+ return r;
59
+ }" " " :: forall a . StrMap a -> StrMap a
60
+
61
+ foreign import _copyEff " " "
62
+ function _copyEff(m) {
63
+ return function () {
64
+ return _copy(m);
65
+ };
66
+ }" " " :: forall a b h r . a -> Eff (st :: ST.ST h | r ) b
67
+
68
+ thawST :: forall a h r . StrMap a -> Eff (st :: ST.ST h | r ) (SM.STStrMap h a )
69
+ thawST = _copyEff
70
+
71
+ freezeST :: forall a h r . SM.STStrMap h a -> Eff (st :: ST.ST h | r ) (StrMap a )
72
+ freezeST = _copyEff
73
+
74
+ foreign import runST " " "
75
+ function runST(f) {
76
+ return f;
77
+ }" " " :: forall a r . (forall h . Eff (st :: ST.ST h | r ) (SM.STStrMap h a )) -> Eff r (StrMap a )
78
+
79
+ pureST :: forall a b . (forall h e . Eff (st :: ST.ST h | e ) (SM.STStrMap h a )) -> StrMap a
80
+ pureST f = runPure (runST f)
81
+
82
+ mutate :: forall a b . (forall h e . SM.STStrMap h a -> Eff (st :: ST.ST h | e ) b ) -> StrMap a -> StrMap a
83
+ mutate f m = pureST (do
84
+ s <- thawST m
85
+ f s
86
+ P .return s)
87
+
46
88
foreign import _fmapStrMap
47
89
" function _fmapStrMap(m0, f) {\
48
90
\ var m = {};\
@@ -137,7 +179,10 @@ foreign import size "function size(m) {\
137
179
\}" :: forall a . StrMap a -> Number
138
180
139
181
singleton :: forall a . String -> a -> StrMap a
140
- singleton k v = insert k v empty
182
+ singleton k v = pureST (do
183
+ s <- SM .new
184
+ SM .poke s k v
185
+ P .return s)
141
186
142
187
foreign import _lookup
143
188
" function _lookup(no, yes, k, m) {\
@@ -150,26 +195,8 @@ lookup = runFn4 _lookup Nothing Just
150
195
member :: forall a . String -> StrMap a -> Boolean
151
196
member = runFn4 _lookup false (P .const true )
152
197
153
- foreign import _cloneStrMap
154
- " function _cloneStrMap(m0) { \
155
- \ var m = {}; \
156
- \ for (var k in m0) {\
157
- \ m[k] = m0[k];\
158
- \ }\
159
- \ return m;\
160
- \}" :: forall a . (StrMap a ) -> (StrMap a )
161
-
162
- foreign import _unsafeInsertStrMap
163
- " function _unsafeInsertStrMap(m, k, v) { \
164
- \ m[k] = v; \
165
- \ return m; \
166
- \}" :: forall a . Fn3 (StrMap a ) String a (StrMap a )
167
-
168
- _unsafeInsert :: forall a . StrMap a -> String -> a -> StrMap a
169
- _unsafeInsert = runFn3 _unsafeInsertStrMap
170
-
171
198
insert :: forall a . String -> a -> StrMap a -> StrMap a
172
- insert k v m = _unsafeInsert (_cloneStrMap m) k v
199
+ insert k v = mutate (\s -> SM .poke s k v)
173
200
174
201
foreign import _unsafeDeleteStrMap
175
202
" function _unsafeDeleteStrMap(m, k) { \
@@ -178,7 +205,7 @@ foreign import _unsafeDeleteStrMap
178
205
\}" :: forall a . Fn2 (StrMap a ) String (StrMap a )
179
206
180
207
delete :: forall a . String -> StrMap a -> StrMap a
181
- delete k m = runFn2 _unsafeDeleteStrMap (_cloneStrMap m) k
208
+ delete k = mutate (\s -> SM .delete s k)
182
209
183
210
alter :: forall a . (Maybe a -> Maybe a ) -> String -> StrMap a -> StrMap a
184
211
alter f k m = case f (k `lookup` m) of
@@ -188,6 +215,12 @@ alter f k m = case f (k `lookup` m) of
188
215
update :: forall a . (a -> Maybe a ) -> String -> StrMap a -> StrMap a
189
216
update f k m = alter (maybe Nothing f) k m
190
217
218
+ fromList :: forall a . [Tuple String a ] -> StrMap a
219
+ fromList l = pureST (do
220
+ s <- SM .new
221
+ for_ l (\(Tuple k v) -> SM .poke s k v)
222
+ P .return s)
223
+
191
224
foreign import _collect
192
225
" function _collect(f) {\
193
226
\ return function (m) {\
@@ -201,9 +234,6 @@ foreign import _collect
201
234
toList :: forall a . StrMap a -> [Tuple String a ]
202
235
toList = _collect Tuple
203
236
204
- fromList :: forall a . [Tuple String a ] -> StrMap a
205
- fromList = foldl (\m (Tuple k v) -> _unsafeInsert m k v) (_cloneStrMap empty)
206
-
207
237
foreign import keys
208
238
" var keys = Object.keys || _collect(function (k) {\
209
239
\ return function () { return k; };\
@@ -214,7 +244,7 @@ values = _collect (\_ v -> v)
214
244
215
245
-- left-biased
216
246
union :: forall a . StrMap a -> StrMap a -> StrMap a
217
- union m1 m2 = fold _unsafeInsert (_cloneStrMap m2) m1
247
+ union m = mutate (\s -> foldM SM .poke s m)
218
248
219
249
unions :: forall a . [StrMap a ] -> StrMap a
220
250
unions = foldl union empty
@@ -223,5 +253,4 @@ map :: forall a b. (a -> b) -> StrMap a -> StrMap b
223
253
map = P .(<$>)
224
254
225
255
instance semigroupStrMap :: (P.Semigroup a ) => P.Semigroup (StrMap a ) where
226
- (<>) m1 m2 = fold f (_cloneStrMap m1) m2 where
227
- f m k v2 = _unsafeInsert m k (runFn4 _lookup v2 (\v1 -> v1 P .<> v2) k m)
256
+ (<>) m1 m2 = mutate (\s -> foldM (\s k v2 -> SM .poke s k (runFn4 _lookup v2 (\v1 -> v1 P .<> v2) k m2)) s m1) m2
0 commit comments