This is the 15th day of my participation in Gwen Challenge

One, foreword

In previous design patterns, we covered the creation pattern of design patterns, which focuses on the way objects are created. For those who want to review:

On singleton pattern

On factory Model

On prototype Model

On the builder model

To extend this creative pattern, we’ll start today by discussing how objects are created and destroyed.

A few questions:

  • 1. When and how to create objects?
  • 2. When and how to avoid creating objects?
  • 3. How to ensure that these objects can be destroyed in a timely manner?
  • 4. What cleaning work should be done before the object is destroyed?

Replace the constructor with a static factory method

What is a constructor? For classes, there is a default public constructor that we can call to generate a new class. This is called a new object, or constructor.

What is the static factory method? The static factory method here is different from, but similar to, the factory method we use in design mode. It returns an instance of a class through a static method. The Boolean type is typical of static factory methods:

    public static Boolean valueOf(boolean b) {
        return (b ? TRUE : FALSE);
    }
Copy the code

That is, replacing the constructor with a static factory method, what is the advantage of doing that?

2.1 advantage

2.1.1 Static factory method has a method name

We know that Java constructors often pass in multiple parameters to construct different objects. Overloaded constructors, if the type and number of arguments are similar, are prone to errors, and are often overwhelmed without reference documentation.

2.1.2 You don’t have to create an object every time you call it

For immutable classes, instances can be created in advance, or cached for reuse, to avoid unnecessary object creation, such as singleton pattern creation, load once, call later.

2.1.3 Can return a subclass of the original return type

This gives you more flexibility in choosing which classes to return objects to, and also responds to the fundamental design pattern principle —- Richter’s Substitution. That is, subclasses should be able to replace parent classes.

A flexible application is to call an API to return an object.

In Java.util. Collections, there are a number of non-shared implementation classes (including unmodifiable Collections, synchronous Collections) for Collections that can be exported using static factory methods and return subclasses of the Collections. The benefit is to reduce the number of apis

public class Collections {
    // Suppresses default constructor, ensuring non-instantiability.
    private Collections() {
    }

 static class UnmodifiableCollection<E> implements Collection<E>, Serializable {
        private static final long serialVersionUID = 1820017752578914078L;

        final Collection<? extends E> c;

        UnmodifiableCollection(Collection<? extends E> c) {
            if (c==null)
                throw new NullPointerException();
            this.c = c;
        }
}
Copy the code

A quick example:

public class Animal{
	publict static Animal getInstance(){
		return new Dog()
	}
}
public class Dog extends Animal(){
}
Copy the code

Calling a parent class produces a return subclass.

Extension:

As of java8, static methods are allowed in interfaces

Since Java9, private static methods are allowed in interfaces

2.1.4 When creating parameter objects, the code is more concise

In the source code, static mode parameter values also change with version. The implementation of EnumSet, for example, depends on the string of the underlying enumeration type. If its element is 64 or less, the RegalarEnumSet instance is issued, and if it is greater than 64, the JumboEnumSet method is returned, unknown to the user.

Of course, this is an example of the source code, the actual inside seems to have not encountered, can be in an object needs multiple fixed call parameters, with a method to encapsulate it, call this method, do not need to pass in a lot of parameters. Of course, this requirement is more demanding.

2.1.5 The class of the object returned by a method may not exist

Using the static factory method, we simply pass in arguments and get an instance of a class that doesn’t exist.

Review the JDBC driver:

Class.forName(driverClass); // Load the MySql Driver class.forname (" com.mysql.jdbc.driver "); DriverManager. GetConnection (" JDBC: mysql: / / 127.0.0.1:3306 / mydb ", "root", "root");Copy the code

By the Drivermanager. GetConnection () returns a concrete implementation class object

2.2 disadvantages

2.2.1 Classes that do not contain public or protected constructors cannot be subclassed.

When a class is inherited, the parent constructor cannot be privatized.

2.2.2 is virtually no different from other static methods

It is generally difficult to find methods that use static factory methods, so you don’t notice the difference between them and other static methods. Therefore, we can identify the use of static factory methods from some common names:

Static factory methods give methods more meaningful names that make it easier to read and write code. Common names are as follows:

From ——- type conversion method, which takes a single argument, such as Data d= date.from (instance)

ValueOf — Less strictly, this method returns instances that have the same values as its arguments. Such static factory methods are really type conversion methods. Of — a more concise alternative to valueOf, used and popular in EnumSet. GetInstance — The returned instance is described by a method parameter, but cannot be said to have the same value as the parameter. For Singleton, this method takes no arguments and returns a unique instance. Create or newInstance — like getInstance, but newInstance ensures that each instance returned is different from all the others. GetType – like getInstance, but used when factory methods are in a different class. Type represents the Type of object returned by the factory method. NewType – like newInstance, but used when factory methods are in different classes. Type represents the Type of object returned by the factory method.

Third, summary

All in all, static factory methods have many advantages that you might want to think about when using the constructor method every day.

Of course, the above problems have not been solved in this article, and then the following article analysis, we will come to them.

Resources: Effective Java (3rd Edition)