I'm a real newbe to clojure and functionnal programming but reading your answer raised a question :
Where do you "store" the stopwatch object which you are passing to all your functions ? I understand that mutability is not needed to develop the functions you described but all of them take a stopwatch as as an argument. This stopwatch must be stored somewhere to call these functions against ? Le samedi 10 décembre 2016 21:51:27 UTC-5, James Reeves a écrit : > > You don't need mutability to represent a stopwatch. > > (defn start [stopwatch] > (assoc stopwatch ::start-time (System/currentTimeMillis))) > > (defn elapsed-since-started [stopwatch] > (- (System/currentTimeMillis) (::start-time stopwatch))) > > (defn stop [stopwatch] > (-> stopwatch > (dissoc ::start-time) > (update ::elapsed (fnil + 0) > (elapsed-since-started stopwatch)))) > > (defn elapsed [stopwatch] > (::elapsed (stop stopwatch) 0) > > (defn reset [stopwatch] > (dissoc stopwatch ::start-time ::elapsed)) > > Mutability is typically only necessary for two reasons: > > 1. Communication across threads > 2. Performance > > - James > > On 10 December 2016 at 07:47, Didier <did...@gmail.com <javascript:>> > wrote: > >> I'm wondering what everyone thinks of using closures to mimic a >> simplistic object system in Clojure? I'm not sure what to think of it yet, >> but the idea is that you wrap object fields inside a closed function, and >> it returns a map of methods that operates over those fields. >> >> Here's an example of using this pattern to implement a StopWatch: >> >> (import [java.lang System]) >> (defn new-stopwatch [] >> (let [start-time (atom nil) >> elapsed (atom 0)] >> {:start (fn [] >> (when (nil? @start-time) >> (reset! start-time (System/currentTimeMillis)))) >> :stop (fn [] >> (when-not (nil? @start-time) >> (reset! elapsed >> (+ @elapsed >> (- (System/currentTimeMillis) @start-time))) >> (reset! start-time nil)) >> @elapsed) >> :reset (fn [] >> (reset! start-time nil) >> (reset! elapsed 0) >> @elapsed) >> :elapsed (fn [] >> (if-not (nil? @start-time) >> (- (System/currentTimeMillis) @start-time) >> @elapsed))})) >> >> (let [sw1 (new-stopwatch) >> sw2 (new-stopwatch)] >> ((:start sw1)) >> ((:start sw2)) >> (Thread/sleep 100) >> ((:reset sw1)) >> ((:start sw1)) >> (println (str "Elapsed for SW1: " ((:elapsed sw1)))) >> (println (str "Elapsed for SW2: " ((:elapsed sw2)))) >> (Thread/sleep 100) >> (println (str "SW1: " ((:stop sw1)))) >> (println (str "SW2: " ((:stop sw2))))) >> >> I find for certain things, like a stopwatch, this pattern is actually >> pretty nice. I can't think of any alternative way to do this in Clojure >> that I'd like better actually. >> >> What are your thoughts? >> >> -- >> You received this message because you are subscribed to the Google >> Groups "Clojure" group. >> To post to this group, send email to clo...@googlegroups.com >> <javascript:> >> Note that posts from new members are moderated - please be patient with >> your first post. >> To unsubscribe from this group, send email to >> clojure+u...@googlegroups.com <javascript:> >> 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 unsubscribe from this group and stop receiving emails from it, send an >> email to clojure+u...@googlegroups.com <javascript:>. >> For more options, visit https://groups.google.com/d/optout. >> > > -- 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 unsubscribe from this group and stop receiving emails from it, send an email to clojure+unsubscr...@googlegroups.com. For more options, visit https://groups.google.com/d/optout.