You can also solve this using `lazy-gen` and `yield-all` from the Tupelo library <https://github.com/cloojure/tupelo#generator-functions-for-lazy-sequences-a-la-python>. It allows you to make a lazy generator function (a la Python):
(let [seq-of-seqs [(range 0 5) (range 10 15) (range 20 25)] flat-seq (lazy-gen (doseq [curr-seq seq-of-seqs] (yield-all curr-seq)))] (is= flat-seq [0 1 2 3 4 10 11 12 13 14 20 21 22 23 24])) Alan On Tue, Nov 21, 2017 at 4:47 PM, Jason Wolfe <ja...@w01fe.com> wrote: > I think this > <https://github.com/plumatic/plumbing/blob/318af7798bb701607aaae8639d12829014941184/src/plumbing/core.cljx#L182> > will do it: > > (lazy-cat (first coll) (when-let [n (next coll)] (lazy-flatten n)))) > > > On Tuesday, November 21, 2017 at 2:34:15 PM UTC-8, Matt Anderson wrote: >> >> I have a function that is returning a lazy-seq of lazy-seq's. >> >> >> (seq (seq [1 2 3]) (seq [4 5 6]) ...) >> >> >> The end-user API, however, should be able to get back a lazy-seq of the >> individual items across all lazy-seq's--essentially a flattening of the >> output of my function--instead of the "top level" seqs. >> >> >> (seq [1 2 3 4 5 6 ...]) >> >> Each of the internal lazy-seq's is expensive in terms of memory usage so >> I'd like to only "load" one at a time. I've been trying to find a way to >> only calculate one of the top-level lazy-seq's at a time and then not >> "take" the next until the user gets to the end of the first and needs the >> first item from the next (eg: (seq [4 5 6]) doesn't get calculated until we >> have consumed 3 and are asking for the next), but haven't found a way to do >> it. Best I've gotten is "loading" 2 "top level" seqs at a time and I'm >> afraid that may be the best I get, but I thought it might be an exercise >> worth presenting in case anyone had ideas. Here's a contrived example: >> >> >> (defn lazy-flatten >> >> [coll] >> >> (when-let [s (seq coll)] >> >> (lazy-seq >> >> (if (seq? (first s)) >> >> (concat (lazy-flatten (first s)) (lazy-flatten (rest s))) >> >> (cons (first s) (lazy-flatten (rest s))))))) >> >> (->> (repeatedly >> (fn [] >> (println "New seq...") >> (map (fn [x] + x (rand-int 10)) (range 4)))) >> lazy-flatten >> (take 1)) >> >> >> >> Prints: >> >> >> New seq... >> >> New seq... >> >> => (8) >> >> >> I realize this is because 2 items must be taken for "concat", so there >> would need to be another approach (this was just my best shot >> implementation). >> >> >> Any ideas on how to get the bottom form to only print 1 "New seq..."? >> > -- > You received this message because you are subscribed to the Google > Groups "Clojure" group. > To post to this group, send email to clojure@googlegroups.com > Note that posts from new members are moderated - please be patient with > your first post. > To unsubscribe from this group, send email to > clojure+unsubscr...@googlegroups.com > For more options, visit this group at > http://groups.google.com/group/clojure?hl=en > --- > You received this message because you are subscribed to the Google Groups > "Clojure" group. > To unsubscribe from this group and stop receiving emails from it, send an > email to clojure+unsubscr...@googlegroups.com. > For more options, visit https://groups.google.com/d/optout. > -- You received this message because you are subscribed to the Google Groups "Clojure" group. To post to this group, send email to clojure@googlegroups.com Note that posts from new members are moderated - please be patient with your first post. To unsubscribe from this group, send email to clojure+unsubscr...@googlegroups.com For more options, visit this group at http://groups.google.com/group/clojure?hl=en --- You received this message because you are subscribed to the Google Groups "Clojure" group. To unsubscribe from this group and stop receiving emails from it, send an email to clojure+unsubscr...@googlegroups.com. For more options, visit https://groups.google.com/d/optout.