2

I've been experimenting with Clojure's multithreading features lately and trying to implement a simple concurrency problem. In the code below I run function write with one agent and try to send a job to another agent, but the program blocks at this line:

(doseq [j (range (count readers))] (send (nth readers j) rr (inc j))) 

Complete code:

(def state (ref 0)) (def readers (doall (map #(agent %) (repeat 3 0)))) (def writers (doall (map #(agent %) (repeat 3 0)))) (defn rr [re] (println (format "Read about %s" @state)) (inc re) ) (defn write [re topic] (dosync (ref-set state topic) ) (Thread/sleep (rand-int 1000)) (println "Wrote about" topic) (doseq [j (range (count readers))] (send (nth readers j) rr (inc j))) (inc re) ) (defn -main[] (dotimes [i 5] (doseq [j (range (count writers))] (send (nth writers j) write (inc j)))) (dorun (map #(await %) writers)) (dorun (map #(println "Writes:" @%) writers)) ) 
1
  • 2
    Just a side comment, it's not particularly idiomatic lisp to put the closed parens in a newline Commented Nov 26, 2011 at 14:23

2 Answers 2

4

I'm not totally sure what you're trying to do but the function rr is defined to take one argument but according to

(send (nth readers j) rr (inc j)) 

it should actually have to take two arguments (the first being the current value of the agent and the second argument is the value of (inc j).

The expression (agent-error (first writers)) should reveal some kind of Arity exception (though I haven't tried it)

Sign up to request clarification or add additional context in comments.

Comments

2

Clojure agents can send to other agents both inside out out of refs and atoms. Any messages sent by the function are held until the change to the agent is finished so you don't have to worry about them racing with themselves.

the main page on agents has an example of arranging agents in a ring

on a side note, If you send messages from within a ref and dosync then the messages are guaranteed to only be sent once, as the transaction commits. In general all the Clojure concurrency tools are designed to compose with both themselves and the other concurrency tools

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.