Map
(/@
) returns the results of the iterations of AssociateTo
in a list and that is confusing you. You can suppress the output by using Scan
instead of Map
. Actually, the output of the mapped function is not of interest to you. What matters is the value of test
afterwards, as AssociateTo
uses call by reference.
test = Association[{a -> 1, b -> 2, c -> 3}]
Scan[
(If[MissingQ[test[#]],
AssociateTo[test, # -> 1],
AssociateTo[test, # -> (test[#] + 1)]
]) &,
{a, b, c, d, e}
];
test
<|a -> 1, b -> 2, c -> 3|>
<|a -> 2, b -> 3, c -> 4, d -> 1, e -> 1|>
Using Scan
instead of Map
increases performance since for returning the intermediate results of AssociateTo
requires copying them. But that is what you actually try to avoid by using AssociateTo
instead of using Associate
recursively.
Here is an illustration of the performance difference:
n = 100000;
a = b = AssociationThread[Range[n], RandomInteger[10, n]];
rand = RandomInteger[n, n];
a == b
Scan[
(If[MissingQ[a[#]],
AssociateTo[a, # -> 1],
AssociateTo[a, # -> (a[#] + 1)]
]) &,
rand
]; // AbsoluteTiming //First
Map[
(If[MissingQ[b[#]],
AssociateTo[b, # -> 1],
AssociateTo[b, # -> (b[#] + 1)]
]) &,
rand
]; // AbsoluteTiming //First
a == b
0.30575
0.517976
True