Factory Design Pattern
The factory method design pattern in java deals with creating objects without having to specify what type of objects to create. It is formally known as the factory pattern and it is a type of the Creational Pattern. Let’s check this pattern with an example.
This design pattern is useful when the calling method doesn’t know which type of object to create at beforehand.
Implementing Factory Pattern
Let’s take the fruits and fruit factory as a real-world example. For this tutorial, first, you need to define a Fruit interface. Next, we shall implement this Fruit into concrete classes. Then, we need to create a Fruit Factory method that supplies fruit based on the input.
The idea here is that, the caller requests the factory for a type of Fruit. The factory then supplies an appropriate Fruit object.
Step 1: Define a Base class
Let’s define an interface for Fruit.
public interface Fruit {
void produceJuice();
}
Code language: Java (java)
We should implement this interface for our concrete classes.
Step 2: Define concrete classes
These are the actual classes for which the Factory creates objects.
public class Banana implements Fruit {
public void produceJuice() {
System.out.println("Here is banana Juice");
}
}
public class Apple implements Fruit {
public void produceJuice() {
System.out.println("Here is apple Juice");
}
}
public class Orange implements Fruit {
public void produceJuice() {
System.out.println("Here is orange Juice");
}
}
Code language: Java (java)
The factory method design pattern in java ensures that callee always uses the Fruit interface. So it doesn’t matter which Fruit it gets. As long as the object has a working produceJuice
method, we are good to go. So now comes the factory implementation.
Step 3: Define a Factory method
The factory method takes one or more parameters to decide what type of object to return. For example, we are using a switch case to create appropriate Fruit
.
public class FruitFactory {
Fruit getFruit(String name) {
switch (name) {
case "apple":
return new Apple();
case "orange":
return new Orange();
case "banana":
return new Banana();
}
throw new RuntimeException("No matching object could be created");
}
}
Code language: Java (java)
As you see, The factory method knows when to supply which object, Also it takes care of the object creation. When the Calling method requests an object to the factory, it creates and provides one. This is why the factory pattern is one of the creational design patterns.
Let’s test the setup in action by writing a main class.
Step 4: Create objects using the Factory pattern
Finally, We need to create a main class that calls the factory method to create objects dynamically at run time.
public class FactoryPatternDemo {
public static void main(String[] args) {
FruitFactory factory = new FruitFactory();
//Create Apple object using factory and call produceJuice method
Fruit fruit = factory.getFruit("apple");
fruit.produceJuice();
//Create Orange object using factory and call produceJuice method
fruit = factory.getFruit("orange");
fruit.produceJuice();
//Create Banana object using factory and call produceJuice method
fruit = factory.getFruit("banana");
fruit.produceJuice();
}
}
Code language: Java (java)
Notice that this approach gives the program to choose the object type at runtime. Also, the callee has no idea which type of object they get. This is because the calling method only knows that it is a Fruit.
Step 5: Test the results of Factory Pattern
If you have done all of these correctly, Then you would see the following output.
Note that the main class didn’t any of the Apple, Orange and Banana classes. But it simply accessed the factory method to create one. As the main method uses the interface to call the produceJuice()
method, all of this was possible at runtime.
Summary
To sum it up, Factory pattern is used when the calling method doesn’t know the type of object beforehand. And interfaces are the key to using different classes with similar implementation at runtime.
If you have not used the factory pattern already, now would the perfect time to start using it. We use the factory methods in java every day without knowing it. For example, Methods like java.lang.Class.newInstance()
, java.sql.DriverManager.getConnection()
and java.lang.Class.forName()
are using the factory pattern.
If you are using Spring Framework then you are most likely using this pattern already.