Observer Design Pattern Explained With Java Sample

What is an Observer Design Pattern?

The Observer Design Pattern is a Behavioral Pattern used to notify all the objects that are registered/attached/added to the same type of observer.


Why use the Observer Design Pattern?

When there is a requirement of "Single object change in its state/behavior/Value needs to notify all other objects which are observing the same object".


Basically, a single object should notify multiple objects of the same observer type. It's the relation of one object to many others.


Players in this pattern:

  • Subject: Provides a contract to add/remove observers

  • ConcreteSubject: Implements a contract defined by Subject

  • Observer: Provides a contract for updating objects when there is a change in the subject state/behavior/Value

  • ConcreteObserver: Implements a contract defined by Observer



Problem definition

Design a software solution for a wholesale pen seller. This wholesale pen seller will sell pens to shops. When there is a change in pen price per market demand, it should automatically notify the change in pen price to all shops.


The players are,

  • Subject – PenSubject

  • ConcreteSubject – Pen

  • Observer – ShopObserver

  • ConcreteObserver – Shop


Below is the PenSubject interface which will define contact for ConcreteSubjects 

public interface PenSubject {  
 void add(ShopObserver shop);  
 void remove(ShopObserver shop);  
 void notifyObservers();  
}  

Below is the Pen class which implements PenSubject Interafce to add/remove Observers and call Notify, which will invoke when there is a change in pen price

import java.util.ArrayList;  
 
public class Pen implements  PenSubject {  
 
 private double _penPrize;  
 
 public Pen(double penPrize)  
    {  
        _penPrize = penPrize;  
    }  
 
 public double getPrize() { return this._penPrize; }  
 public void setPrize(double penPrize) {  
 if(this._penPrize!=penPrize) {  
 this._penPrize = penPrize;  
 this.notifyObservers();  
        }  
    }  
 
 private ArrayList<com.sample.ShopObserver>  shops = new ArrayList<>();  
 
 @Override 
 public void add(ShopObserver shop) {  
        shops.add(shop);  
    }  
 
 @Override 
 public void remove(ShopObserver shop) {  
        shops.remove(shop);  
    }  
 
 @Override 
 public void notifyObservers() {  
       shops.forEach(a->a.update(this));  
       System.out.println("----------------------------------------------------------");  
    }  
}  

Below is the ShopObserver (Observer) interface which defines a contract for ConcreteObserver (i.e. in our case Shop)

public interface ShopObserver {  
 void update(Pen pen);  
}  

Below is the Shop class which implements ShopObserver to update the Subject object

public class Shop implements ShopObserver {  
 
 private String _shopName;  
 
 public Shop(String shopName)  
    {  
        _shopName = shopName;  
    }  
 
 @Override 
 public void update(Pen pen) {  
        System.out.println("pen prize changed to " +  pen.getPrize() + " in " + _shopName);  
    }  
}  

We will see the execution and the result now 

public class Main {  
 
 public static void main(String[] args) {  
        Pen pen = new Pen(10);  
        pen.add(new Shop("Shop1"));  
        pen.add(new Shop("Shop2"));  
        pen.add(new Shop("Shop3"));  
 
        pen.setPrize(20);  
        pen.setPrize(25);  
        pen.setPrize(30);  
    }  
}  

Below is the result screenshot. In the result, we can see that change in pen price value has notified all shops



Summary

In this article, we have learned through code example what Observer design pattern is, as well as why and where to use it.


Source: C# Corner

Recent Posts

See All

Singleton Design Pattern with Java

Singleton Design Pattern As the name suggests “single” i.e has only one instance and provides a global instance. Singleton design pattern restricts the instantiation of a class and ensures that one ob