Skip to content

Instantly share code, notes, and snippets.

@kriyative
Created May 10, 2012 23:30
Show Gist options
  • Save kriyative/2656568 to your computer and use it in GitHub Desktop.
Save kriyative/2656568 to your computer and use it in GitHub Desktop.
First cut implementation of `with-progress` and `report!`
(def ^{:dynamic true} *print-progress* true)
(defmacro with-progress
"Bind a `reportfn` function, and evaluate `body` wherein
calling (report!) will invoke the report function with the current
state of the iteration."
[reportfn & body]
`(let [iter# (atom 0)
reporter# ~reportfn]
(letfn [(~'report! []
(when *print-progress*
(swap! iter# inc)
(reporter# (deref iter#))))]
~@body)))
(defn fprint [& more]
"Same as print but explicitly flushes *out*."
(apply print more)
(flush))
(defn fprintln
"Same as println but explicitly flushes *out*."
[& more]
(apply println more)
(flush))
(defn make-standard-reporter
"Generate a standard reporter function which can be passed to
`with-progress`."
[n & {:keys [ncols line-handler]}]
(fn [i]
(cond
(zero? (mod i n))
(fprintln (format "%,8d rows%s"
i
(if line-handler (str " " (line-handler i)) "")))
(zero? (mod i (int (/ n (or ncols 70))))) (fprint "."))))
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment