My Dev weblog

Just another development weblog

The Observer Pattern

leave a comment »

As programs grow and get more complex. the Communication between classes problems grow bigger and bigger.
to deomenstrate the two-way communcation Problem, consider the followuing example:

A Window object contains one or more UI objects inside it, say a progress bar.  So, the Window object contains a progress bar object inside it as a memeber variable. The window object has a complete control of the Progress bar object – because it owns it !!. So, when the window object wants to Communicate with the progress bar, it will simply call one of  its  methods. BUT WHAT to do if the progress bar object wants to Communicate with its parent Window??

The Observer Design Pattern is the pattern to solve such problems – among other similar problems. It allows 2-way communication between multiple Classes.  The pattern consists of the following participant classes:

  1. Subject: This is an interface to provide the methods that allow the progress Bar object to communicate with its Container Object – the Window-. The Subject interface provides the following APIs:
    • Attach() : to add an observer to track my changes.
    • Notify() : this method does the actual Communication between the Class and the Observer(s).
  2. Concrete Subject: the Actual class that needs to inform its owner with the change in its state, in our case, it will be the Progress Bar object.
  3. Observer: The interface that provides the ability to listen and react to the sent messages from the Concrete Subjects. it has a very important abstract method called update() which is Called by the Subject when sendin a message.
  4. Concrete Observer: this Class is the One Listening for the messages sent from the Concrete Subject object. It is the Consumer of its messages.

The following Class Diagram shows the classes of the observer pattern:

the Class Diagram of the Observer pattern

the Class Diagram of the Observer pattern

So, the following scinario occurs when applying the pattern :

  1. The Concrete Observer – the Window Object in our example- owns the Concrete Subject – the Progress Bar – and can communicate with it via calling its public methods. The normal Case
  2. When the Concrete Subject – the Progress Bar- wants to communicate with a Observer – the Window, it will Call its inherited method notify() – the mothod in the interface Subject-, the Notify() method will look for all observers and call their update() methods.
  3. The message has arrived to the Observer(s) – in our case, the Window Object. and we acheives the 2-way communication.

Java has provided the mechanism to make it easy for us to implement the observer pattern.The Subject and Observer are generic interfaces interfaces. So, we can write them only once and implement them in our actual code.
Java – since JDK 1.o- provided an interface called Observer that has only one abstract method called update(Observable o, Object arg).

Java also provided a class Observable that contains the APIs used to communicate with the classes implementing the Observer interface – i.e call their update() method-. The Most important APIs are:

  1. addObserver(Observer o)
  2. setChanged()
  3. notifyObservers()

Let’s see the following Java example that demonstrates how to use the Observer/Observable classes.
In this example we have 2 Classes: BigClass and Sub. Normally, the BigClass object has a member of class Sub. We will make the sub Object count from 1 to SIZe, and if it reaches a given number- say 4 – it will notify its owner class – the BigClass object- that it has reached the given number

//*********** BigClass.java ***************//
import java.util.Observable;
import java.util.Observer;</code>

public class BigClass implements Observer {

private Sub theSub = null;

public BigClass(Sub theSub) {
System.out.println("in  the BC constr");
this.theSub = theSub;
}

public void startCount(){
theSub.startCount();
}

public void update(Observable obs, Object obj) {
if (obs == theSub) {
System.out.println("the value: "+theSub.getValue()+" was reached!");
}
}
}

//************** Sub.java **************//
import java.util.Observable;

class Sub extends Observable {

private int n = 0;
private final int SIZE = 100;

public Sub(int n) {
System.out.println("in the sub cons");
this.n = n;
}

public void setValue(int n) {
this.n = n;

}

public int getValue() {
return n;
}

void startCount() {
for (int counter = 0; counter &lt; SIZE; counter++) {
if (counter == this.n) {
setChanged();
notifyObservers();
}//end if
}//end for loop
}//end method
}

and now, we will use them both in the main method
public class Main {
public Main() {
Sub theSubObject = new Sub(45);
BigClass theBigObject = new BigClass(theSubObject);
theSubObject.addObserver(theBigObject);
theSubObject.setValue(44);
theBigObject.startCount();
}

public static void main(String[] args) {
Main m = new Main();
}
}

look at the code; we created objects for both Classes BigCalss, Sub. then we Told the Sub object to set the BigClass Object as its Observer :
theSubObject.addObserver(theBigObject);
Then, we started Counting ….. now, if we stumbled upon the given value, the Sub object will notify its observer – the BigClass Object by following sequence:
setChanged();
notifyObservers();
this sequence will send the message to the observer Object – the BigClass in our example.

As you can see, it is very easy to implement the observer pattern using java.

Advertisement

Written by topquarck

February 15, 2009 at 11:30 pm

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Connecting to %s

Follow

Get every new post delivered to your Inbox.