Fix fiber aware combinators to use general iteration instead of fiber

specifics.
This commit is contained in:
Calvin Rose 2021-08-06 16:17:47 -05:00
parent 2e641a266d
commit bb5c3773f1
2 changed files with 21 additions and 23 deletions

View File

@ -1031,14 +1031,23 @@
(set k (next ind k))) (set k (next ind k)))
ret) ret)
(defn- resume-n (defn- take-n-fallback
[n fib] [n xs]
(def res @[]) (def res @[])
(var taken 0) (when (> n 0)
(while (and (< taken n) (fiber/can-resume? fib)) (var left n)
(let [elem (resume fib)] (each x xs
(+= taken 1) (array/push res x)
(array/push res elem))) (-- left)
(if (= 0 left) (break))))
res)
(defn- take-until-fallback
[pred xs]
(def res @[])
(each x xs
(if (pred x) (break))
(array/push res x))
res) res)
(defn- slice-n (defn- slice-n
@ -1053,19 +1062,9 @@
"Take the first n elements of a fiber, indexed or bytes type. Returns a new array, tuple or string, respectively." "Take the first n elements of a fiber, indexed or bytes type. Returns a new array, tuple or string, respectively."
[n ind] [n ind]
(cond (cond
(fiber? ind) (resume-n n ind)
(bytes? ind) (slice-n string/slice n ind) (bytes? ind) (slice-n string/slice n ind)
(slice-n tuple/slice n ind))) (indexed? ind) (slice-n tuple/slice n ind)
(take-n-fallback n ind)))
(defn- resume-until
[pred fib]
(def res @[])
(while (fiber/can-resume? fib)
(let [elem (resume fib)]
(if (pred elem)
(break)
(array/push res elem))))
res)
(defn- slice-until (defn- slice-until
[f pred ind] [f pred ind]
@ -1078,9 +1077,9 @@
"Same as `(take-while (complement pred) ind)`." "Same as `(take-while (complement pred) ind)`."
[pred ind] [pred ind]
(cond (cond
(fiber? ind) (resume-until pred ind)
(bytes? ind) (slice-until string/slice pred ind) (bytes? ind) (slice-until string/slice pred ind)
(slice-until tuple/slice pred ind))) (indexed? ind) (slice-until tuple/slice pred ind)
(take-until-fallback pred ind)))
(defn take-while (defn take-while
`Given a predicate, take only elements from a fiber, indexed or bytes type that satisfy `Given a predicate, take only elements from a fiber, indexed or bytes type that satisfy

View File

@ -54,8 +54,7 @@
(assert (deep= (take 3 (generate [x :in [1 2 3 4 5]] x)) @[1 2 3]) "take from fiber") (assert (deep= (take 3 (generate [x :in [1 2 3 4 5]] x)) @[1 2 3]) "take from fiber")
# NB: repeatedly resuming a fiber created with `generate` includes a `nil` as # NB: repeatedly resuming a fiber created with `generate` includes a `nil` as
# the final element. Thus a generate of 2 elements will create an array of 3. # the final element. Thus a generate of 2 elements will create an array of 3.
(assert (= (length (take 4 (generate [x :in [1 2]] x))) 3) "take from short fiber") (assert (= (length (take 4 (generate [x :in [1 2]] x))) 2) "take from short fiber")
(assert-error :invalid-type (take 3 {}) "take 6")
# take-until # take-until