Factory mode of design mode

Factory mode can be divided into three modes: simple factory, factory method and abstract factory

Usage scenario

Generally speaking, there are two usage scenarios of factory mode:

  1. The creation process of a single object is complex, such as an object that needs complex initialization operations
  2. You need to create different objects according to different types

For the three modes of subdivision, the use scenarios can be distinguished:

  1. When the object creation logic is simple, you usually only need to create new. At this time, you can consider the simple factory mode
  2. When the object creation logic is very complex and various initialization operations need to be done, consider using the factory method mode to split the complex logic of object creation into various factory classes, so that each factory class will not be too complex
  3. When there is more than one product family in the system and only one product family is used at a time, the abstract factory pattern is used

Simple factory mode

Class diagram

ProcuctA and ProductB inherit the Product abstract class, and ProductFactory returns different Product instances according to the passed in type

code implementation

Product

public abstract class Product {
    public abstract void use();
}

ProductA

public class ProductA extends Product {
    @Override
    public void use() {
        System.out.println("You are using ProductA...");
    }
}

ProductB

public class ProductB extends Product {
    @Override
    public void use() {
        System.out.println("You are using ProductB...");
    }
}

ProductFactory

public class ProductFactory {
    public Product createProduct(String type) {
        Product product = null;
        if ("A".equals(type)) {
            product = new ProductA();
        } else if ("B".equals(type)) {
            product = new ProductB();
        }
        return product;
    }
}

Main

public class Main {
    public static void main(String[] args) {
        ProductFactory factory = new ProductFactory();
        Product product;

        product = factory.createProduct("A");
        product.use();

        product = factory.createProduct("B");
        product.use();
    }
}

comment

When adding different products frequently, you need to frequently modify the if/else logic in the ProductFactory

application

JDK

java.text.DateFormat#getDateInstance()
java.text.DateFormat#getDateInstance(int)
java.text.DateFormat#getDateInstance(int, java.util.Locale)

Encryption class to obtain key generators of different encryption algorithms:

KeyGenerator keyGen=KeyGenerator.getInstance("DESede");

Factory method model

Class diagram

Compared with a simple factory, this method defines the ProductFactory as an abstract class, and then creates different specific productafactories and productbfctories. It determines which factory and object to create during use, avoiding if/else judgment

code implementation

Product

public abstract class Product {
    public abstract void use();
}

ProductA

public class ProductA extends Product {
    @Override
    public void use() {
        System.out.println("You are using ProductA...");
    }
}

ProductB

public class ProductB extends Product {
    @Override
    public void use() {
        System.out.println("You are using ProductB...");
    }
}

ProductFactory

public abstract class ProductFactory {
    public abstract Product createProduct();
}

ProductAFactory

public class ProductAFactory extends ProductFactory {
    @Override
    public Product createProduct() {
        return new ProductA();
    }
}

ProductBFactory

public class ProductBFactory extends ProductFactory {
    @Override
    public Product createProduct() {
        return new ProductB();
    }
}

Main

public class Main {

    public static void main(String[] args) {
        ProductFactory factory;
        Product product;

        factory = new ProductAFactory();
        product = factory.createProduct();
        product.use();

        factory = new ProductBFactory();
        product = factory.createProduct();
        product.use();
    }

}

comment

This mode is more in line with the opening and closing principle, but it is very similar to the original new ProductA() and new ProductA(). The introduction of factory mode makes the design more complex.

application

JDBC

Connection conn=DriverManager.getConnection("jdbc:mysql://127.0.0.1:3306/db1","db_user","123456");
Statement statement=conn.createStatement();
ResultSet rs=statement.executeQuery("select * from user");

Abstract factory pattern

To understand the abstract factory pattern, we need to understand two concepts:

  • Product hierarchy structure: the product hierarchy structure is the inheritance structure of the product. For example, if an abstract class is a TV, and its subclasses include Haier TV, Hisense TV and TCL TV, a product hierarchy is formed between the abstract TV and the TV of a specific brand. The abstract TV is the parent class, and the TV of a specific brand is its subclass.
  • Product family: in the abstract factory model, product family refers to a group of products produced by the same factory and located in different product hierarchy, such as Haier TV and Haier refrigerator produced by Haier Electric Appliance Factory. Haier TV is located in the TV product hierarchy and Haier refrigerator is located in the refrigerator product hierarchy.

In the factory method mode, specific factories are responsible for producing specific products, and each specific factory corresponds to a specific product. Generally, there is only one factory method or a set of overloaded factory methods in a specific factory. But sometimes we need a factory that can provide multiple product objects instead of a single product object.

Class diagram

Factory1 is responsible for creating ProductA1 and ProductB1
Factory2 is responsible for creating ProductA2 and ProductB2
The client does not need to know the specific product, but only needs to know the factory created to use the product

code implementation

AbstractProductA

public abstract class AbstractProductA {

    public abstract void use();

}

ProductA1

public class ProductA1 extends AbstractProductA {

    @Override
    public void use() {
        System.out.println("You are using ProductA1...");
    }

}

ProductA2

public class ProductA2 extends AbstractProductA {

    @Override
    public void use() {
        System.out.println("You are using ProductA2...");
    }

}

AbstractProductB

public abstract class AbstractProductB {

    public abstract void eat();

}

ProductB1

public class ProductB1 extends AbstractProductB {

    @Override
    public void eat() {
        System.out.println("You are eating ProductB1...");
    }

}

ProductB2

public class ProductB2 extends AbstractProductB {

    @Override
    public void eat() {
        System.out.println("You are eating ProductB2...");
    }

}

AbstractFactory

public abstract class AbstractFactory {

    public abstract AbstractProductA createProductA();

    public abstract AbstractProductB createProductB();

}

Factory1

public class Factory1 extends AbstractFactory {

    @Override
    public AbstractProductA createProductA() {
        return new ProductA1();
    }

    @Override
    public AbstractProductB createProductB() {
        return new ProductB1();
    }

}

Factory2

public class Factory2 extends AbstractFactory {

    @Override
    public AbstractProductA createProductA() {
        return new ProductA2();
    }

    @Override
    public AbstractProductB createProductB() {
        return new ProductB2();
    }

}

Main

public class Main {

    public static void main(String[] args) {
        AbstractFactory factory;
        
        factory = new Factory1();
        use(factory);

        factory = new Factory2();
        use(factory);
    }

    public static void use(AbstractFactory factory) {
        AbstractProductA productA = factory.createProductA();
        productA.use();
        AbstractProductB productB = factory.createProductB();
        productB.eat();
    }

}

comment

Abstract factory pattern brings many classes, the structure is relatively complex, and it is troublesome to create a new product hierarchy.
Abstract factory mode has few application scenarios in practical work. Just pay attention to it

Keywords: Design Pattern

Added by vigiw on Mon, 24 Jan 2022 14:54:02 +0200