This page is not created by, affiliated with, or supported by Slack Technologies, Inc.
2023-09-12
Channels
- # ai (1)
- # announcements (7)
- # babashka (32)
- # beginners (23)
- # biff (9)
- # calva (1)
- # cljs-dev (13)
- # clojure (32)
- # clojure-belgium (1)
- # clojure-chicago (15)
- # clojure-europe (24)
- # clojure-india (3)
- # clojure-nl (3)
- # clojure-norway (55)
- # clojure-uk (4)
- # clojurebridge (1)
- # clojurescript (5)
- # core-async (17)
- # data-science (9)
- # datomic (29)
- # events (3)
- # fulcro (16)
- # graalvm-mobile (4)
- # helix (15)
- # hyperfiddle (74)
- # introduce-yourself (1)
- # jobs (4)
- # kaocha (12)
- # leiningen (27)
- # lsp (16)
- # shadow-cljs (6)
- # spacemacs (20)
- # sql (27)
- # squint (7)
- # tools-deps (29)
- # vim (2)
- # xtdb (10)
I'm reducing over a collection, and I need to take from a channel inside of the reducing function.
(reduce (fn [acc item]
(update acc :x conj (<! (get-some-async-stuff acc item)))))
{}
items)
This doesn't work because I need to be in a go-block and that means the accumulator needs to be a channel and everything gets messy very quickly. Is there a recipe for this sort of a thing, or is it just messy? I've started trying to implement via pipeline-async or maybe using transducers, but if this is a familiar problem I'd welcome some advice.Turn it into a map instead of a reduce, use pipeline for the map, use async/into to turn the result of the pipeline back into a collection
The problem was a little more complex, it's a series of nested reduces for traversing arbitrarily-shaped trees. I ended up rewriting it as go-loops, which is less elegant but does the job.
reduce is particularly problematic because it is sort of its own callback based system (which is what CollReduce is) and that conflicts with the callback system that core.async is
Yeah, I really wanted to try it as a transducer on a chan, but I wasn't able to make it work and loop was just sitting there the whole time.
I have played around a little bit with a version of iteration that iterates a process (a thing that runs over time on some channels) instead of a function, and I wonder what that would look like for reduce
(the reduce-async above is fine, but doesn't scratch that itch because af is a function that returns a channel, not a process)
I've been playing around with Promesa's csp namespace with virtual threads and I think for green field work in the future I'll be skipping core.async - it's so much easier to just block and have the runtime do the right thing. Virtual threads are really great!
I guess, promesa's csp too me looks like a rather mechanical copying of parts of core.async's api, without fixing any of the internal issues in core.async(particularly the resource handling around alts), using virtual threads, which are a brand spanking new feature.
I think that's a pretty on-the-nose description. I do like that go
just spawns a vthread instead of doing the whole state-machine macro dance, and all the limitations that brings, but obviously core.async couldn't do that because vthreads are new. And I also like the core promise library so using csp is just an extra bonus.
https://downey.family/p/2023-09-12/async-reduce.clj.html maybe something like this is the higher order async-reduce, not sure anyone would actually want it ever