Hi Bill,
Thanks, that's a good point re: await. It would also be interesting to
have the agents run for a certain length of time, rather than a
certain number of iterations.
What do you think of using a map argument to a reduce fn? Idiomatic
Clojure seems to prefer using a vector, but I am biased toward a map
based on Ruby experience. I haven't decided which is more readable.
Stuart
> Hi Stuart,
>
> On Mon, Oct 27, 2008 at 7:06 PM, Stuart Halloway
> <[EMAIL PROTECTED]> wrote:
>>
>> Hi all,
>>
>> The code below implements a Monte Carlo simulation to estimate the
>> value of pi. It works, and it was easy to reuse the original single-
>> threaded approach across multiple agents.
>>
>> How idiomatic is this use of agents? Other than bringing in ForkJoin,
>> are there other idiomatic ways to parallelize divide-and-conquer in
>> Clojure?
>>
>> Cheers,
>> Stuart
>>
>> (defn in-circle? [[x y]]
>> (<= (Math/sqrt (+ (* x x) (* y y))) 1))
>>
>> (defn random-point []
>> [(dec (rand 2)) (dec (rand 2))])
>>
>> ; take samples, tracking number that land
>> ; :in circle and :total number
>> (defn sample-for-pi [count]
>> (reduce (fn [{in :in total :total} point]
>> {:in (if (in-circle? point) (inc in) in)
>> :total (inc total)})
>> {:in 0 :total 0}
>> (take count (repeatedly random-point))))
>>
>>
>> (defn guess-from-samples [samples]
>> (assoc samples :guess (/ (* 4.0 (:in samples)) (:total samples))))
>>
>> ; guess pi by running Monte Carlo simulation count times
>> (defn guess-pi [count]
>> (guess-from-samples (sample-for-pi count)))
>>
>> ; guess pi by running Monte Carlo simulation count times
>> ; spread across n agents
>> (defn guess-pi-agent [n count]
>> (let [count (quot count n)
>> agents (for [_ (range n)] (agent count))]
>> (doseq a agents (send a sample-for-pi))
>> (apply await agents)
>> (guess-from-samples (reduce (fn [a1 a2]
>> {:in (+ (:in @a1) (:in @a2))
>> :total (+ (:total @a1) (:total
>> @a2))})
>> agents))))
>
> I've not gotten around to playing with the concurrency features of
> Clojure yet, so I'm just commenting "theoretically" on your code. In
> "guess-pi-agent", you use "await" to wait for the results from the
> agents. If one of the agents "dies", won't your code wait forever? I
> would think that it would be preferable to use "await-for" (with a
> timeout) so that the result can still be guessed based on the samples
> that have come back from the other agents. If you plan to use a
> variation of this code in a multi-processor example, some degree of
> agent failure is even more likely.
>
> --
> Bill Clementson
>
> >
--~--~---------~--~----~------------~-------~--~----~
You received this message because you are subscribed to the Google Groups
"Clojure" group.
To post to this group, send email to [email protected]
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
-~----------~----~----~----~------~----~------~--~---