Having worked on Clojure benchmarks on the Computer Language Benchmarks Game web site, that is sometimes the kind of Clojure code one needs to write if you want it to be as fast as it can be.
http://shootout.alioth.debian.org/u64q/compare.php?lang=clojure Also, splitting it out into smaller chunks, if by that you mean functions, requires care in Clojure to avoid boxing and unboxing of primitive numbers. It is possible, but can be an additional hurdle when trying to optimize code. Macros can be better in that regard. Another comment, Cedric: Consider writing that part of your code in Java and call it from Clojure. Java is to Clojure as in-line assembler is to C, except that it isn't in-line :-) Andy On Nov 9, 2012, at 8:57 AM, Yakovlev Roman wrote: > what a mess if it is a function it's huuge did you try split it to useful > chunks ? it's just unreadable and that's why you cann't spot anything i > guess.. > > пятница, 9 ноября 2012 г., 0:48:20 UTC+4 пользователь Cedric Greevey написал: > I have the following code to perform a complicated image convolution. It > takes 10-15 seconds with output dimensions 256x256 and samples 6. No > reflection warnings, and using unchecked math doesn't speed it up any. I've > tried to ensure it uses primitive math inside the loops, aside from > generating the outer loop's values. What cached-load-chunk does shouldn't > matter much, but in most cases it should boil down to a map lookup inside a > swap! and a couple of atom derefs and function calls. The bottleneck is > likely in the math somewhere, and likely something is being boxed, though > I've primitive-coerced every numerical let and loop value and avoided more > than two arguments per arithmetic op. > > Can anyone spot anything I haven't that could be causing boxed arithmetic > inside the loops? > > (let [^BufferedImage out (BufferedImage. width height > BufferedImage/TYPE_INT_BGR) > half-w (double (/ width 2.0)) > half-h (double (/ height 2.0)) > lnk (double (- (* (Math/log 0.1) (inc l10-mag)) > (/ (Math/log (+ (* half-w half-w) (* half-h half-h))) > 2))) > cconv (double (/ chunk-width (* 2.0 Math/PI))) > c-base-ln (double (* chunk-base-mag (Math/log 0.1))) > x-offset (double (* chunk-width (+ 0.5 (/ deg-rot 360)))) > fmtstr (str "%0" chunk-name-digits "d") > cached-load-chunk (cached-objects > (fn [chunk-num] > (maybe-load-image > (str chunk-name-base > (format fmtstr (inc chunk-num)) > ".png"))))] > (doseq [oy (range height) ox (range width)] > (let [ox (int ox) > oy (int oy) > ix (double (- ox half-w)) > iy (double (- oy half-h)) > samples (double samples) > smo (int (dec samples))] > (loop [sx (int 0) sy (int 0) ns (double 0) > r (double 0) g (double 0) b (double 0)] > (if (== sy samples) > (.setRGB out ox oy (int (+ > (int (/ b ns)) > (+ (* 256 (int (/ g ns))) > (* 65536 (int (/ r ns))))))) > (let [nsx (int (if (== sx smo) 0 (inc sx))) > nsy (int (if (zero? nsx) (inc sy) sy)) > ix (double (+ ix (/ (+ sx (rand)) samples))) > iy (double (+ iy (/ (+ sy (rand)) samples)))] > (if (and (== ix 0) (== iy 0)) > (recur nsx nsy ns r g b) > (let [lnz-P (double (+ lnk (/ (Math/log (+ (* ix ix) (* iy > iy))) 2))) > argz-P (double (+ Math/PI (Math/atan2 iy ix))) > ; atan2 output range is -pi...pi and oy increases down > the screen > x (double (* argz-P cconv)) > y (double (* (- c-base-ln lnz-P) cconv)) > ; > chunk-num (int (/ y chunk-height)) > chunk-x (int (rem (int (+ x x-offset)) chunk-width)) > chunk-y (int (- y (* chunk-height chunk-num))) > ^BufferedImage chunk (cached-load-chunk chunk-num) > pixel (int (if chunk (.getRGB chunk chunk-x chunk-y) 0)) > r (double (+ r (/ (bit-and pixel 0x00ff0000) 65536))) > g (double (+ g (/ (bit-and pixel 0x0000ff00) 256))) > b (double (+ b (bit-and pixel 0x000000ff)))] > (recur nsx nsy (inc ns) r g b)))))))) > out)) > > > -- > 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 -- 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