The Abstract Factory pattern provides an interface that delegates creation calls to one or more concrete classes in order to deliver specific objects. Following is the definition provided for the pattern in the GoF book on Design Patterns: Abstract Factory provides an interface for creating families of related or dependent objects without specifying their concrete classes. Abstract factory relies on object composition – i.e. object creation is implemented in methods exposed in the factory methods. The intent of the pattern is to create families of related objects without having to depend on their concrete classes. First we define the interface and implementation of the object that we want to create: public interface Car { public void setDescription(String description); public void refuel(); } public class EVCar implements Car { @Override public void setDescription(String description) { // set description } @Override public void refuel() { // electric charging } } public class HybridCar implements Car { @Override public void setDescription(String description) { // set description } @Override public void refuel() { // refuel with gas } } Now we define the factories, starting with an abstract factory: public interface AbstractCarFactory { public Car createCar(); } Next the actual implementations of the factory: public class EVCarFactory implements AbstractCarFactory { @Override public Car createCar() { EVCar evCar = new EVCar(); return evCar; } } public class HybridCarFactory implements AbstractCarFactory { @Override public Car createCar() { HybridCar hybridCar = new HybridCar(); return hybridCar; } } Now let's test drive this factory: public class AbstractFactoryTest { AbstractCarFactory abstractCarFactory = null; @Test public void evCarFactoryTest() { abstractCarFactory = new EVCarFactory(); abstractCarFactory.createCar(); } @Test public void hybridCarFactoryTest() { abstractCarFactory = new HybridCarFactory(); abstractCarFactory.createCar(); } } While the pattern hides the implementation details from the client, there is always a chance that the underlying system will need to change – for example new attributes might be added to Car or AbstractCarFactory, which would mean a change to the interface that the client was relying on, thus breaking the API.
Saturday, September 07, 2013
Abstract Factory
Posted by Sathish at 9/07/2013 10:58:00 AM 0 comments
Tuesday, August 13, 2013
Priority Queue
Posted by Sathish at 8/13/2013 02:10:00 AM 0 comments
Monday, March 18, 2013
Factory Method Pattern
The Factory Method Pattern encapsulates object creation by letting subclasses decide what objects to create. The creator class defines an abstract factory method that the subclasses implement to produce products.
Factory method is known as a creational pattern - it's used to construct objects such that they can be decoupled from the implementing system.
The GoF book on Design Patterns defines it as -
Define an interface for creating an object, but let the subclasses decide which class to instantitate. The Factory method lets a class defer instantiation to subclasses.
In this definition the term "interface" is used in the general sense, meaning - a concrete class implementing a method from a supertype (a class or interface).
The Factory method builds on the concept of a Simple Factory, but lets the sub-classes decide which implementation of the concrete class to use. Simple factory is a programming idiom rather than a pattern, where object creation is relegated to a method. Factory Method pattern builds on it - deferring object creation to sub-classes.
A simple factory can also be defined as a static method and is often called a static factory. This way we don’t have to instantiate an object to make use of the create method. But the disadvantage is that, we can’t subclass and change the behavior of the create method.
Example code from http://java.dzone.com/articles/design-patterns-factory. First an interface and an implementation for the product:
public interface Logger { public void log(String message); }
public class XmlLogger implements Logger { @Override public void log(String message) { System.err.println(message); } }Creator with the abstract factory method:
public abstract class AbstractLoggerCreator { //factory method public abstract Logger createLogger(); public Logger getLogger() { Logger logger = new XmlLogger(); return logger; } }Now the concrete creator class:
public class XmlLoggerCreator extends AbstractLoggerCreator { @Override public Logger createLogger() { XmlLogger logger = new XmlLogger(); return logger; } }Finally the client code to test the pattern:
public class FactoryMethodClient { private void methodA(AbstractLoggerCreator creator) { Logger logger = creator.createLogger(); logger.log("message"); } public static void main(String[] args) { AbstractLoggerCreator creator = new XmlLoggerCreator(); FactoryMethodClient client = new FactoryMethodClient(); client.methodA(creator); } }Downside of the pattern is that it might be over-complicated. In a lot of cases, a simple factory pattern will work fine. The FactoryMethod just allows further decoupling, leaving it to the sub-classes of the Creator to decide which type of concrete Product to create.
Posted by sathish at 3/18/2013 01:22:00 AM 0 comments
Labels: design, design pattern, java
Thursday, March 07, 2013
Data Structures - Queue
A Queue is an example of a linear data structure - a sequential
collection, and it is a FIFO structure. Anything that's inserted
first, will be the first to leave. We need to maintain two pointers,
the start and the end. An efficient implementation of Queue performs
the operations - enqueue (insert) and dequeue (remove) - in O(1) time.
Below is a sample implementation of a Queue (Java Data Structures (2nd edition))
public class Queue { private Object[] objArray; private int start, end; private boolean full; public Queue(final int maxSize) { objArray = new Object[maxSize]; start = end = 0; full = false; } public boolean isEmpty() { return (start == end) && !full; } public boolean isFull() { return full; } public void insert(final Object o) { if (!full) { objArray[start = (++start % objArray.length)] = o; } if (start == end) { full = true; } } public Object remove() { if (full) { full = false; } else if (isEmpty()) { return null; } return objArray[end = (++end % objArray.length)]; } public String toString() { StringBuilder sbr = new StringBuilder(); for (int i = 0; i < objArray.length; i++) { sbr.append(objArray[i]); } return sbr.toString(); } }
Posted by sathish at 3/07/2013 12:20:00 AM 0 comments
Labels: data structures, design, java