(ns sleeping-barber
(:require [clojure.core.async :as async :refer [<! <!! >! go]]
[clojure.core.async.timeout :refer [timeout]]))
(defn sleep-millis [min max]
(+ min (rand-int (- max min))))
(defn wait-for-customer []
(Thread/sleep (sleep-millis 10 30)))
(defn haircut []
(Thread/sleep 20))
(defn customer [barber-chair waiting-room]
(go
(wait-for-customer)
(if (not (async/put! waiting-room :customer))
(println "No chair available. Customer leaves.")
(do
(async/<! barber-chair) ; Wait for barber chair to be available
(println "Customer sits in the barber chair.")
(async/>! barber-chair :customer) ; Signal the barber
(println "Barber starts giving a haircut.")
(haircut)
(println "Haircut finished. Customer leaves.")
(recur barber-chair waiting-room)))))
(defn barber [barber-chair waiting-room]
(go-loop []
(let [customer (async/<! waiting-room)]
(if (= customer :customer)
(do
(println "Barber wakes up and starts giving a haircut.")
(haircut)
(println "Haircut finished. Barber goes back to sleep.")
(async/>! barber-chair :chair)
(recur))
(recur))))
(defn simulate-haircuts []
(let [barber-chair (async/chan)
waiting-room (async/chan 3)]
(async/go
(barber barber-chair waiting-room))
(doseq [i (range 10)]
(customer barber-chair waiting-room))
(println "Simulation completed."))
;; Wait for the simulation to complete
(Thread/sleep 10000))
(simulate-haircuts)
To embed this program on your website, copy the following code and paste it into your website's HTML: