I was just trying to demonstrate laziness to someone, and I wrote a simple recursive function to process a list.
I assumed that it would be fine on an infinite list. But suddenly I got a "too much recursion" internal error.
Huh? I always write code that does that kind of thing. What's the problem?
But of course, normally I use built-in functions like map
as the basis of other list-processing functions. This time I was trying to write my own recursive traversal. And, of course, that can't possibly work.
Here's what I wrote.
(defn q [xs]
(if (empty? xs) ()
(cons (* (first xs) (first xs)) (q (rest xs)) )))
(take 10 (q (cycle '(1 2 3 4))))
So, how, in fact DO I write my own traversal functions that can handle lazy data structures in Clojure? Is there some kind of equivalent of a "yield"?
(defn q [xs]
(if (empty? xs) ()
(lazy-seq ;; <- here's our magic!
(cons (* (first xs) (first xs)) (q (rest xs)) ))))
(take 10 (q (cycle '(1 2 3 4))))