Over a million developers have joined DZone.

Clojure, Java, and Sleeping Barbers

DZone's Guide to

Clojure, Java, and Sleeping Barbers

· Java Zone ·
Free Resource

Verify, standardize, and correct the Big 4 + more– name, email, phone and global addresses – try our Data Quality APIs now at Melissa Developer Portal!

My friend Matt wrote a pretty rad (yep, I used that word) implementation of the “sleeping barber” program in Clojure. Matt’s code had an almost sentence-like simplicity to it – pithy but expressive — that impressed me.

As we walked through how the program worked, I couldn’t help but wonder about a Java implementation. So, I wrote one.

package name.christianson.mike;

import java.util.concurrent.BlockingQueue;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.LinkedBlockingQueue;
import java.util.concurrent.atomic.AtomicBoolean;
import java.util.concurrent.atomic.AtomicInteger;
import static java.util.concurrent.TimeUnit.*;

public class BarberShop {
	public static final int NUM_WAITING_ROOM_CHAIRS = 3;
	public static final long SHOP_RUNTIME_MILLIS = SECONDS.toMillis(10);
	private final static AtomicBoolean shopOpen = new AtomicBoolean();
	private final static AtomicInteger totalHaircuts = new AtomicInteger();
	private final static AtomicInteger lostCustomers = new AtomicInteger();
	private final BlockingQueue<Object> waitingRoom = new LinkedBlockingQueue<>(NUM_WAITING_ROOM_CHAIRS);

	public static void main(String[] args) throws InterruptedException {
		BarberShop shop = new BarberShop();

		ExecutorService executor = Executors.newFixedThreadPool(3);
		Runnable customerGenerator = new CustomerGenerator(shop);
		Runnable barber = new Barber(shop);
		Runnable progressTracker = new ProgressTracker(shop);

	private void close() {

	private void open() {

	public boolean isOpen() {
		return shopOpen.get();

	public boolean seatCustomerInWaitingRoom(Object customer) {
		boolean customerSeated = waitingRoom.offer(customer);
		if(!customerSeated) {
		return customerSeated;
	public Object napUntilCustomerArrives() throws InterruptedException {
		return waitingRoom.take();

	public void recordHaircut() {

	public Object lostCustomers() {
		return lostCustomers.get();

	public Object haircuts() {
		return totalHaircuts.get();


Matt’s is self-contained in one file while mine is split across multiple files. (I opted to not use anonymous/inner classes.) I think we were a bit surprised that the concurrency logic is similar and the ”main” driving section of each implementation follows the same set-up procedure. Perhaps my code was influenced by way of transliteration?

I’m struck by how Matt’s Clojure programs reads somewhat like a story while my Java program reads like instructions for a computer.


Developers! Quickly and easily gain access to the tools and information you need! Explore, test and combine our data quality APIs at Melissa Developer Portal – home to tools that save time and boost revenue. 


Published at DZone with permission of

Opinions expressed by DZone contributors are their own.

{{ parent.title || parent.header.title}}

{{ parent.tldr }}

{{ parent.urlSource.name }}