introduce
Intent: provide an interface to create a series of related or interdependent objects without specifying their specific classes.
Main solution: mainly solve the problem of interface selection.
When to use: the system has more than one product family, and the system only consumes one family of products.
How to solve: in a product family, define multiple products.
Key code: aggregate multiple similar products in one factory.
Application example: for work, in order to attend some parties, there must be two or more sets of clothes, such as business clothes (complete sets, a series of specific products), fashion clothes (complete sets, a series of specific products), and even for a family, there may be business women's clothes, business men's clothes, fashion women's clothes, fashion men's clothes, which are also complete sets, that is, a series of specific products. Product. Suppose a situation (in reality, it doesn't exist, otherwise, it's impossible to enter communism, but it's helpful to explain the abstract factory mode), in your home, a certain wardrobe (specific factory) can only store a certain kind of such clothes (complete set, a series of specific products), and each time you take this complete set of clothes, you will naturally take it out of this closet. With the idea of OOP, all the wardrobes (concrete factories) are one of the wardrobes (Abstract factories), and each complete set of clothes includes specific tops (a specific product), pants (a specific product). These specific tops are actually tops (Abstract products), and specific pants are pants (another Abstract product).
Advantage: when multiple objects in a product family are designed to work together, it can ensure that clients always use only the objects in the same product family.
Disadvantages: product family extension is very difficult. To add a series of a product, you need to add code in both abstract creators and concrete ones.
Usage scenario: 1. QQ skin replacement, a whole set of skin replacement. 2. Generate programs of different operating systems.
Note: product family is difficult to expand, and product grade is easy to expand.
Realization
We will create the Shape and Color interfaces and entity classes that implement them. The next step is to create the abstract factory class AbstractFactory. Then define the factory classes ShapeFactory and ColorFactory, both of which extend AbstractFactory. Then create a factory creator / generator class, FactoryProducer.
AbstractFactoryPatternDemo, our demo class uses FactoryProducer to get AbstractFactory objects. It will pass Shape information (CIRCLE / RECTANGLE / SQUARE) to AbstractFactory to get the type of object it needs. It also passes Color information (RED / GREEN / BLUE) to AbstractFactory to get the type of object it needs.
Step 1
Create an interface for the shape.
Create the entity class that implements the interface.
public interface Shape { void draw(); } public class Rectangle implements Shape { @Override public void draw() { System.out.println("Inside Rectangle::draw() method."); } } public class Square implements Shape { @Override public void draw() { System.out.println("Inside Square::draw() method."); } } public class Circle implements Shape { @Override public void draw() { System.out.println("Inside Circle::draw() method."); } }
Step 2
Create an interface for colors.
Create the entity class that implements the interface.
public interface Color { void fill(); } public class Red implements Color { @Override public void fill() { System.out.println("Inside Red::fill() method."); } } public class Green implements Color { @Override public void fill() { System.out.println("Inside Green::fill() method."); } } public class Blue implements Color { @Override public void fill() { System.out.println("Inside Blue::fill() method."); } }
Step 3
Create abstract classes for Color and Shape objects to get the factory.
public abstract class AbstractFactory { public abstract Color getColor(String color); public abstract Shape getShape(String shape) ; }
Step 4
Create the factory class that extends AbstractFactory, and generate the object of entity class based on the given information.
public class ShapeFactory extends AbstractFactory { @Override public Shape getShape(String shapeType){ if(shapeType == null){ return null; } if(shapeType.equalsIgnoreCase("CIRCLE")){ return new Circle(); } else if(shapeType.equalsIgnoreCase("RECTANGLE")){ return new Rectangle(); } else if(shapeType.equalsIgnoreCase("SQUARE")){ return new Square(); } return null; } @Override public Color getColor(String color) { return null; } }
public class ColorFactory extends AbstractFactory { @Override public Shape getShape(String shapeType){ return null; } @Override public Color getColor(String color) { if(color == null){ return null; } if(color.equalsIgnoreCase("RED")){ return new Red(); } else if(color.equalsIgnoreCase("GREEN")){ return new Green(); } else if(color.equalsIgnoreCase("BLUE")){ return new Blue(); } return null; } }
Step 5
Create a factory creator / generator class to get the factory by passing shape or color information.
public class FactoryProducer { public static AbstractFactory getFactory(String choice){ if(choice.equalsIgnoreCase("SHAPE")){ return new ShapeFactory(); } else if(choice.equalsIgnoreCase("COLOR")){ return new ColorFactory(); } return null; } }
Step 6
Use FactoryProducer to get AbstractFactory, and pass type information to get object of entity class.
public class AbstractFactoryPatternDemo { public static void main(String[] args) { //Get shape factory AbstractFactory shapeFactory = FactoryProducer.getFactory("SHAPE"); //Get objects with the shape of Circle Shape shape1 = shapeFactory.getShape("CIRCLE"); //Call the draw method of Circle shape1.draw(); //Get object with Rectangle shape Shape shape2 = shapeFactory.getShape("RECTANGLE"); //Call the draw method of Rectangle shape2.draw(); //Get objects with Square shape Shape shape3 = shapeFactory.getShape("SQUARE"); //Call Square's draw method shape3.draw(); //Get color factory AbstractFactory colorFactory = FactoryProducer.getFactory("COLOR"); //Get objects with Red color Color color1 = colorFactory.getColor("RED"); //Call Red's fill method color1.fill(); //Get object with color Green Color color2 = colorFactory.getColor("Green"); //Call Green's fill method color2.fill(); //Get objects with Blue color Color color3 = colorFactory.getColor("BLUE"); //Call Blue's fill method color3.fill(); } }
Step 7
Execute the program and output the result:
Inside Circle::draw() method. Inside Rectangle::draw() method. Inside Square::draw() method. Inside Red::fill() method. Inside Green::fill() method. Inside Blue::fill() method.