Skip to content

Instantly share code, notes, and snippets.

@angerman
Created December 1, 2009 09:44
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save angerman/246189 to your computer and use it in GitHub Desktop.
Save angerman/246189 to your computer and use it in GitHub Desktop.
;; Worker agents are there to be dipatched to, they state should be incremented
;; on each completed work unit
(def *worker* (map #(agent -1 :meta {:no %}) (range 5)))
;; a simualted work unit for the worker
(defn work-unit [s n]
(Thread/sleep 1000)
;;(send printer println+ (format "%s: %d" (str *agent*) n))
(inc s))
;; the printer agent coordinates the printing to the console
;; alternativly using a logfile
(def printer (agent nil :meta {:out *out*}))
;; the printer's println funktion
(defn println+ [_ msg] (binding [*out* (:out ^*agent*)] (println msg)))
;; The tasks agent, holds all the current tasks to be executed
(def taskmaster (agent (range 60)))
;; Takes an additional agent, and dispatches the first task from the queue (agents state) to the
;; specified agent
(defn next+ [tasks agent]
(if-let [task (first tasks)]
(do
(send printer println+ (format "Dispatched Task %d to Agent No.: %d (completed: %d)" task (:no ^agent) @agent))
(send agent work-unit task)
(drop 1 tasks))))
;; hookup the taskmaster as a watcher over his workers
(doseq [worker *worker*]
(add-watcher worker :send taskmaster next+))
;; remove the taskmaster
(doseq [worker *worker*]
(remove-watcher worker taskmaster))
;; start the agents:
(doseq [worker *worker*]
(send worker inc))
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment