Changing (concat primes [k]) to (conj primes k) gave me an order of magnitude performance increase.
On Jan 24, 1:19 pm, Nebojsa Stricevic <nebojsa.strice...@gmail.com> wrote: > Greetings, > > I'm new to Clojure and working my way through Project Euler problems > for learning. I stuck with problem 7, not with solution, but with > performance. My code needs about 90sec to find solution. > > (ns problem7) > > (defn no-dividers? > "checks if number can be divided with any of dividers" > [number dividers] > (let [divs (take-while #(<= % (. Math sqrt number)) dividers)] > (reduce #(and %1 (pos? (rem number %2))) > true > divs))) > > (defn find-primes [n] > "finds first n primes" > (loop [primes [2 3] x 1 f -] > (if (= (count primes) n) > primes > (let [k (f (* 6 x) 1)] > (recur > (if (no-dividers? k primes) (concat > primes [k]) primes) > (if (= f -) x (inc x)) > (if (= f -) + -)))))) > > (find-primes 10001) > > And, for example, this code is much faster: > > (defn div? [n d] > (= 0 (rem n d))) > > (defn smallest-prime-factor [number] > (loop [n number d 2] > (cond (> d (int (Math/sqrt number))) n > (= n d) n > (div? n d) d > true (recur n (inc d))))) > > (def primes (lazy-cat '(2 3) > (filter #(= %1 (smallest-prime-factor %1)) > (take-nth 2 (iterate inc 5))))) > > (nth primes 10001) > > Now, since i have advanced a bit in reading about Clojure, I know that > preferred solution would be by using lazy sequences, but my concern is > about performance of my solution, no mater how bad is with style. > > I should probably say that my background is pure imperative (mostly > Java, C/C++...). > > Thanks in advance. -- 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