Tuesday, April 15, 2014

Factory Pattern in Java


Harry works at take away counter of a food joint.


What is Harry’s job?
  1. He takes an order
  2. Passes a slip back in kitchen with order no. and food item on it
  3. Gets back a food package from kitchen with order no. on it
  4. Announce the order no.
  5. Take payment and give order and bill to customer

It’s a simple job and Harry is good at it.
Why?
Because he does not have to worry what’s going on in kitchen. How is food being prepared? What is the recipe? What if there are no tomatoes and chef has to put tomato puree instead? He doesn’t have to deal with all these problems.
So, the creation of food item is hidden from him. Hiding the food creation part from Harry has made his job very simple. Just imagine if he has to prepare the food himself too. How complicated it will get for him?

Nice story but how is it related to Java or Factory pattern in java?


To understand it lets translate it into java-


serviceCustomer()  in above code is a simple method with all the logic from taking the order to delivering it.
It has following parts-
  1. generate order no.
  2. Prepare food item
  3. generate bill
  4. announce order no.
  5. deliver order
Logic to prepare food item is marked as Creation logic.
Based on the food ordered, say Pizza. Object of the class is created 
Pizza pizza = new Pizza();
Some work on the object is done-
pizza.addCheese();
pizza.addTopping();

What's the problem with this?

This creation logic is based on the food item ordered. To keep it simple we have only shown it for Pizza and Burger but imagine how big this logic will be for complete menu. And code will be very hard to maintain.

Imagine if a new item is added to the menu this code will have to be changed. The method will have to be tested again. And if some careless coder makes a mistake. All the customers will get impacted as serviceCustomer method has the bug. 

Solution-
Let's go back to the Take Away Counter example we discussed in the beginning. 
If you see the tasks being done in serviceCustomer() method again-

  1. generate order no.
  2. Prepare food item
  3. generate bill
  4. announce order no.
  5. deliver order
Harry was doing everything highlighted in Green

Why was Harry's job so simple?

Because he didn't have to worry about the preparation of food items.(Point 2)
So if we take out this part from serviceCustomer() the method will become perfect like Harry's job.

But where will this task go?
In the Kitchen of course that's where all the food is prepared.


















Creation logic has been transferred to Kitchen class. Now serviceCustomer() looks much simple and manageable.



















You may be wondering, why we created a separate class when we could have just created a separate method getFoodItems in TakeAwayCounter.
TakeAwayCounter is just one client of getFoodItems.But it can be used by other classes(clients). Say for example HomeDeliveryCounter or ServiceCounter.
Basic idea of separating the logic in a separate class Kitchen is to keep all these clients which are now using getFoodItems or any future client free from any impact due to change in creation logic.

By creating Kitchen class we have succeeded in separating the creation logic. Kitchen here is an example of java factory.

  • Java Factory hides the creation logic from client


Kitchen is of no use if food is not sent back to the customer and is lying in the Kitchen itself.
So, we also have to return the food item object example Pizza or Burger to the calling method.
Harry never knew what used to be inside the food package. For him every food item used to come inside a food package. Similarly Factory in java returns every object casted under the cover of interface.

As we know a method can return only one type. So, how can different types (Pizza Burger) returned from same method.
Answer is inheritance.

Pizza and Burger Implements FoodParcel interface so, getItems return FoodParcel. Any new food item will have to inherit FoodParcel.

Another important point about java factory is-

  •  Returns object casted as Interface.
This is how the complete thing will work in java-
  • FoodParcel is our Interface. 
  • All food items implement it.(Pizza, Burger)
  • TakeAwayCounter is a client which need an object of food items(Pizza, Burger)
  • Kitchen is our factory which creates Object of food items. Cast them as FoodParcel and return to the client.




















Factory Pattern in Java-




















This is how it works-

  1. Creation logic is hidden in Factory
  2. All products implements AbstractProduct interface
  3. Client requests for an object from factory
  4. Factory creates object of type Product(Concrete) and cast it to AbstractProduct(Interface)
  5. Client uses the object cast as AbstractProduct
  6. As this pattern is a solution for object creation so, this comes under type Creational Patterns

visit ApexInformatix.com for Online/Classroom course on Java and other technologies

2 comments: