[Edit: How do you properly format code on this site? I tried and couldn't figure it out, so I just left it as markdown.]
Would you still consider adding the variadic cases of `update-keys` and `update-vals`? I found this thread after being surprised that my use case wasn't supported and I think I have a pretty compelling example showing that this is desirable.
I have a data structure like this (and a predicate to be used later):
```
(def data {:foo {0 {:bar [10 42 11 12]}
1 {:bar [20 21 42 22]}
,,, }})
(def my-special-pred (complement #{42}))
```
(Note that there can be arbitrarily many items in the `(data :foo)` map; the three commas are supposed to look like an ellipsis.)
Suppose I want to update the vector at `:foo 0 :bar`. This could be done with:
```
(update data :foo update 0 update :bar (partial filter my-special-pred))
```
In that case you could also just use `update-in` (and you probably should). But what if you want to do this for _all_ of the values in the :foo map, not just the one at 0? You _should_ be able to just use:
```
(update data :foo update-vals update :bar (partial filter my-special-pred))
```
But you can't, because `update-vals` only takes 2 arguments. Instead, you need to do something like:
```
(update data :foo update-vals #(update % :bar (partial filter my-special-pred)))
```
This is more inconvenient than it first looks; since anonymous function literals are not allowed to be nested, you can't use another one (e.g.) for the predicate. With a variadic `update-vals` though, you could do this:
```
(update data :foo update-vals update :bar (partial filter #(not= 0 (mod % 42))))
```
For the same reason, you can't easily use multiple "levels" of `update-vals`, like this:
```
(def data2 {0 {:top 200
:bottom 201
,,, }
1 {:left 300
:right 301
,,, }})
(update-vals data2 update-vals inc)
```
There are various ways you can work around this, but by far the cleanest and best seems to be to just write your own `update-vals` function that wraps the existing one:
```
(defn update-vals [m f & args]
(clojure.core/update-vals m #(apply f % args)))
```
With that defined, *all* of the examples in this comment work as expected. And since this is an "accreting change" (it's a strict superset of existing functionality), it's fully backwards compatible, and could (and should) be included in the core library.
(Also, for the record, the `data2` example is contrived, but the other one is structurally identical to actual code that I just wrote for my project, and I will be using the variadic `update-vals` wrapper.)