clojure - Improve performance of a ClojureScript program -


i have clojurescript program performs math calculations on collections. developed in idiomatic, host-independent clojure, it's easy benchmark it. surprise (and contrary answers suggest which faster, clojure or clojurescript (and why)?), same code in clojurescript runs 5-10 times slower clojure equivalent.

here did. opened lein repl , browser repl @ http://clojurescript.net/. tried these snippets in both repls.

 (time (dotimes [x 1000000] (+ 2 8)))   (let [coll (list 1 2 3)] (time (dotimes [x 1000000] (first coll)))) 

then opened javascript console @ browser repl , wrote minimalist benchmark function,

 function benchmark(count, fun) {    var t0 = new date();    (i = 0; < count; i++) {      fun();    }    var t1 = new date();    return t1.gettime() - t0.gettime();  } 

back browser repl:

 (defn multiply [] (* 42 1.2)) 

then try both native javascript multiplication, , clojurescript variant in javascript console,

 benchmark(1000000, cljs.user.multiply);   benchmark(1000000, function(){ 42 * 1.2 }); 

what found

  • native javascript math comparable math in clojure
  • clojurescript 5-10 times slower either of them

now question is, how can improve performance of clojurescript program?

there approaches i've considered far

  • fall using mutable javascript arrays , objects behind scenes. (is possible @ all?)
  • fall using native javascript math operators. (is possible @ all?)
  • use javascript arrays explicitly (aget js/v 0)
  • use less ambitious implementation of clojure-for-javascript, https://github.com/chlorinejs/chlorine or https://github.com/gozala/wisp generate more idiomatic javascript, don't support namespaces 'm using lot.

javascript has explicit return, so

function () { 42 * 1.2 } 

does nothing; you'll want benchmark

function () { return 42 * 1.2 } 

instead. happens clojurescript version compiles to, there won't difference (in clojurescript, basic arithmetic functions in non-higher-order usage inlined regular operator-based javascript expressions).

now, clojure faster clojurescript @ point. part of reason clojure still more tuned clojurescript, although clojurescript improving @ pretty great pace in department. part clojure has more mature jit take advantage of (the modern js engines, v8 in particular, pretty great, not quite hotspot-grade yet).

the magnitude of difference tricky measure, though; fact jits involved means loop body free of side effects, such 1 in question, optimized away, possibly on first run through (through use of on-stack replacement, used hotspot , i think v8 -- i'd have check sure though). so, better benchmark like

(def arr (long-array 1))  ;;; benchmark (dotimes [_ 1000000]   (aset (longs arr) 0 (inc (aget (longs arr) 0)))) 

(longs call avoid reflection in clojure; use ^longs hint).

finally, case, in both clojure , clojurescript, kinds of particularly performance-sensitive code it's best use native arrays , such. happily, there's no problem doing so: on clojurescript side, you've got array, js-obj, aget, aset, make-array, can use :mutable metadata on fields in deftype able set! them in method bodies etc.


Comments

Popular posts from this blog

Pull out data related to my apps from Android Play Store and iOS App Store -

Change php variable from jquery value using ajax (same page) -

How can I fetch data from a web server in an android application? -