wait & notify

Wait, Notify and NotifyAll in Java

Posted on Updated on

java-logo

 

 

 

It’s became most frequently asked interview question for any level of experience. In this articles we will discuss about wait, notify and notifyAll methods of Object class that help you to make understand about it.

First of all, wait, notify and notifyAll methods are belong to Object class which is final and used to communicate between threads or we can say inter communication between threads on same lock.

A lock is a guard that protect the Object/resource to being access concurrently in multi threading environment and ensure that it will be exclusive available or only one thread can acquire a lock on a Object at a time and rest of the thread will wait in waiting Set until lock get released by acquired thread.

Wait :- It block the current thread execution until  notify/notifiyAll method get called on same lock object. As a Thread call wait(), lock get released and current thread get suspended.

notify:- It wake up only one thread waiting on the same lock and that thread (waiting thread) start execution.

notifyAll :- It wake up all the threads that waiting on same lock. ( CPU scheduler decides which thread wake up first ).

Wait, notify and notifyAll are worked on same object lock. Suppose a thread t1 is waiting on lock A1 object and subsequently another thread t2 send the notification by notify method on same lock A1 then t1 Thread get woke up. If t2 send a notification to another object then t1 never wake up and keep running in suspend mode.

Here, Let’s see in this program how two thread communicate to each other on same lock ( MessageEvent’s object). When Queue’s capacity reach to MAX size then Producer thread hang on their execution and wait for notification. In the same way as Consumer Thread only send the notified on same object when Queue capacity reach down to Zero.
Consumer.Java


package com.waitAndNotify.example;
/**
 * 
 * @author #Ajay
 *
 */
public class Consumer implements Runnable {
	private MessageEvent event;

	Consumer(MessageEvent e) {
		this.event = e;
	}

	public void run() {
			while (true) {
				synchronized (event) {
				if (event.getStorage().size() == 0) {
					event.notify();
				}
				
				try {
					Thread.sleep(600);
				} catch (InterruptedException e) {
					e.printStackTrace();
				}
				System.out.println(event.getStorage().size()+"Removing Element from Queque "
						+ event.getStorage().poll());
			}
		}
	}
}


Producer.Java


package com.waitAndNotify.example;
/**
 * 
 * @author #Ajay
 *
 */
import java.util.Date;

public class Producer implements Runnable {

	private MessageEvent event;

	Producer(MessageEvent e) {
		this.event = e;
	}

	public void run() {
		
		while (true) {
			synchronized (event) {
				try {
					if (event.getStorage().size() == event.getMaxSize()) {
						event.wait();
					}
					event.getStorage().add(new Date());
					System.out.println("Adding Element into Queque ");
					
				} catch (InterruptedException e) {
					e.printStackTrace();
				}
				try {
					Thread.sleep(500);
				} catch (InterruptedException e) {
					// TODO Auto-generated catch block
					e.printStackTrace();
				}
			}

		}
	}

}



MessageEvent.Java


package com.waitAndNotify.example;
/**
 * 
 * @author #Ajay
 *
 */
import java.util.Date;
import java.util.LinkedList;
import java.util.Queue;

public class MessageEvent {

	private final int maxSize;
	private final Queue storage;

	public MessageEvent() {
		this.maxSize = 10;
		this.storage = new LinkedList();
	}

	public int getMaxSize() {
		return maxSize;
	}

	public Queue getStorage() {
		return storage;
	}
}

WaitNotifyMainTest.Java


package com.waitAndNotify.example;
/**
 * 
 * @author #Ajay
 *
 */
public class WaitNotifyMainTest {
	
	public static void main(String args[]){
		MessageEvent storage = new MessageEvent();
		Producer producer = new Producer(storage);
		Consumer consumer = new Consumer(storage);
		Thread t1 = new Thread(producer,"Producer");
		Thread t2 = new Thread(consumer,"Consumer");
		
		t1.start();
		t2.start();
		
	}

}

Output here :- 
Adding Element into Queque 
Adding Element into Queque 
Adding Element into Queque 
Adding Element into Queque 
Adding Element into Queque 
Adding Element into Queque 
Adding Element into Queque 
Adding Element into Queque 
Adding Element into Queque 
Adding Element into Queque 
10Removing Element from Queque Tue Oct 06 21:14:41 IST 2015
9Removing Element from Queque Tue Oct 06 21:14:42 IST 2015
8Removing Element from Queque Tue Oct 06 21:14:42 IST 2015
7Removing Element from Queque Tue Oct 06 21:14:43 IST 2015
6Removing Element from Queque Tue Oct 06 21:14:43 IST 2015
5Removing Element from Queque Tue Oct 06 21:14:44 IST 2015
4Removing Element from Queque Tue Oct 06 21:14:44 IST 2015
3Removing Element from Queque Tue Oct 06 21:14:45 IST 2015
2Removing Element from Queque Tue Oct 06 21:14:45 IST 2015
1Removing Element from Queque Tue Oct 06 21:14:46 IST 2015

 

Please remember, Inter communication never be happened on two different object lock if so then each thread start running separately or Waiting thread is  suspended permanently.

I hope, it would be helpful!!!