I tried to leave a comment on your blog, but it's not clear to me if it's being held for moderation, or simply failed. So I'll paste it here too.
On Tue, Sep 30, 2008 at 10:06 AM, Fogus <[EMAIL PROTECTED]> wrote: > > In an attempt to get a feel for Clojure I have started porting Paul > Graham's "On Lisp". This is cool. "On Lisp" is what convinced me Lisp was actually worth understanding, and without that I would never have given Clojure a chance. > Feel free to tear my source to shreds whenever I am breaking Clojure > idioms and/or simply incorrect in my comments. Since you're inviting comments... remove-if uses "regular" recursion, but because the JVM does not optimize away tail calls the way Common Lisp (usually) does, this could fail for very long lists. However, if you just replace "cons" with "lazy-cons" and the other recursive call with "recur", you'll have a beautiful lazy sequence function that will never blow the call stack. I'm sure you've noticed that Graham is taking some pains to make tail-recusive versions of his functions. In general to take advantage of this you'll want to use "recur" instead of the tail call. It's more idiomatic (and more succinct!) to say (if (seq lst) ...) than (if (nil? lst) nil ...) Also better to use (let [tri (fn [c n] ...)] (tri 0 n)) than to have a defn nested inside another defn, since the inner defn is still defining a namespace-global name, even though it's nested. Finally I noticed your clever use of Java arrays to get mutability. This is fine, in that you'll often find yourself in Clojure working with mutable Java objects, and you just have to deal with it. However, Clojure also provides some very nice multi-threading features if you use refs of immutables instead of mutable objects. In your case, you could replace (let [counter (to-array [0])] ...) with (def counter (ref 0)). Then use @counter instead of aget, and use (dosync (set-ref ...)) instead of aset. For more details on refs, see http://clojure.org/refs Anyway, don't let me discourage you -- I'm sure working through On Lisp will be a great way for you to learn Clojure, and will likely help others too. I'm very interested to see the DSLs of the later chapters in Clojure. Keep it up! --Chouser --~--~---------~--~----~------------~-------~--~----~ 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 To unsubscribe from this group, send email to [EMAIL PROTECTED] For more options, visit this group at http://groups.google.com/group/clojure?hl=en -~----------~----~----~----~------~----~------~--~---