Permalink
Browse files

CLJS-491: avoid layered subvecs

cljs.core/build-subvec now checks whether its vector argument is
already a Subvec and, if so, unwraps it, so that the return value of
cljs.core/subvec is always a view on a regular vector. This is in line
with the behaviour of subvec in Clojure.

Includes a basic test.
  • Loading branch information...
1 parent 69741f2 commit 3ca249a5a3ad07586c91b143463374a89d1fcf25 @michalmarczyk michalmarczyk committed with swannodette Apr 1, 2013
Showing with 11 additions and 7 deletions.
  1. +9 −7 src/cljs/cljs/core.cljs
  2. +2 −0 test/cljs/cljs/core_test.cljs
@@ -3359,13 +3359,15 @@ reduces them without incurring seq initialization"
(-lookup coll k not-found)))
(defn- build-subvec [meta v start end __hash]
- (let [c (count v)]
- (when (or (neg? start)
- (neg? end)
- (> start c)
- (> end c))
- (throw (js/Error. "Index out of bounds")))
- (Subvec. meta v start end __hash)))
+ (if (instance? Subvec v)
+ (recur meta (.-v v) (+ (.-start v) start) (+ (.-start v) end) __hash)
+ (let [c (count v)]
+ (when (or (neg? start)
+ (neg? end)
+ (> start c)
+ (> end c))
+ (throw (js/Error. "Index out of bounds")))
+ (Subvec. meta v start end __hash))))
(defn subvec
"Returns a persistent vector of the items in vector from
@@ -1047,6 +1047,8 @@
(assert (= :fail (try (subvec v2 6 10) (catch js/Error e :fail))))
(assert (= :fail (try (subvec v2 6 10) (catch js/Error e :fail))))
(assert (= :fail (try (subvec v2 3 6) (catch js/Error e :fail))))
+ ;; no layered subvecs
+ (assert (identical? v1 (.-v (subvec s 1 4))))
)
;; TransientVector

0 comments on commit 3ca249a

Please sign in to comment.