Tassilo Horn <tass...@member.fsf.org> writes:

> I think, you are looking for `realized?`.  Here's a function for
> creating a vector of realized elements of a lazy seq.
>
> user> (defn realized-vec [s]
>       (loop [s s, r []]
>          (if (and (seq s) (realized? (rest s)))
>             (recur (rest s) (conj r (first s)))
>             (conj r (first s)))))

Another note: the (seq s) call for testing if the seq is exhausted [and
also the (rest s) call] will force the realization of the current item.
As a result, the function will at least realize one element, although
the given lazy seq may be completely unrealized.

Here's a better version that doesn't force realization.

--8<---------------cut here---------------start------------->8---
user> (defn my-realized? [s]
        (or (not (instance? clojure.lang.IPending s))
            (realized? s)))

(defn realized-vec [s]
  (loop [s s, r []]
    (if (and (my-realized? s) (seq s))
      (recur (rest s) (conj r (first s)))
      r)))

(def nums (iterate inc 0))
#'user/nums
user> (realized-vec nums)
[0]
user> (take 10 nums)
(0 1 2 3 4 5 6 7 8 9)
user> (realized-vec nums)
[0 1 2 3 4 5 6 7 8 9]
user> (def r (range))
#'user/r
user> (realized-vec r)
[]
user> (take 5 r)
(0 1 2 3 4)
user> (realized-vec r)
[0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 
29 30 31]
--8<---------------cut here---------------end--------------->8---

Note that `range` returns a so-called chunked lazy seq, where
realization always happens is chunks of 32 elements.

Bye,
Tassilo

-- 
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

Reply via email to