ES6 Iterators should use IIterable if possible

Description

Motivation:

ES6 Iterables: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Iteration_protocols

Use in React: https://github.com/facebook/react/blob/30dac4e78de02fb427ee82013160ae875128d7a2/packages/react/src/ReactElementValidator.js#L195-L204

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 (defn es6-iterator** [coll] (if (implements? IIterable coll) (let [it (-iterator ^not-native coll)] #js{:next (fn [] (if ^boolean (.hasNext it) #js{:value (.next it), :done false} #js{:value nil, :done true}))}) ;; Fallback to naive first/next iterator: (ES6Iterator. (seq coll)))) ;; Tests can use round trip: (es6-iterator-seq (es6-iterator (hash-map 0 1 2 3))) (defn es6-iter-consume [it] (while (not (.-done (.next it))))) (dotimes [_ 3] (let [xs (vec (range 3000)) runs 1000] (simple-benchmark [] (es6-iter-consume (es6-iterator xs)) runs) (simple-benchmark [] (es6-iter-consume (es6-iterator** xs)) runs)))

About a 4x speedup in Chrome. Also note that much less garbage is produced.

Environment

None

Status

Assignee

Unassigned

Reporter

Andre R

Labels

Approval

None

Patch

None

Affects versions

1.9.908

Priority

Minor