Consider using static factory methods instead of construction methods

Source: Internet
Author: User

Creating an object construction method creating an object

In Java, the common way to create objects is to create them through public construction methods ;

For example, here is a constructor for the Boolean class, and a Boolean object created by the constructor method;

     Public Boolean (String s) {        this(ToBoolean (s));    }
New Boolean ("true");
Static Factory methods Create objects

In fact, there is another way to create objects, using public static factory methods to create objects, but this method is often easy to be ignored by programmers;

For example, here is the ValueOf method for the Boolean class, and the Boolean instance returned through the static factory method, noting that the Boolean instance object is not created here, but instead returns a pre-created Boolean object;

     Public Static Boolean valueOf (String s) {        return ToBoolean (s)?  True:false;    }
Boolean btrue = boolean.valueof ("true");
Note the distinction between static factory methods and factory method patterns

Note that the static factory method and the factory method pattern in the design pattern are not a concept:

    • The static factory method usually refers to a static method in a class, and by invoking the static method, an instance belonging to the class is obtained;
    • Factory method mode is a design pattern, refers to the specific factory object is responsible for the production of specific product objects, which involves a variety of factories (classes), a variety of objects (classes), such as memory factory production memory objects, CPU factory production CPU objects;

However, if you want to say something similar, the static factory approach is a little bit like the simple factory model, but the difference is quite large, the static factory method in simple Factory mode creates a variety of different objects (not homogeneous instances), whereas the static factory method generally creates only one instance (including subclasses) belonging to the class;

Advantages of using static factory methods 1, more readable

Suppose we need to write a class that produces a random number.RandomIntGenerator,该类有两个成员属性:最小值min和最大值max,

Suppose our requirement is to create three types of RandomIntGenerator objects,

1, greater than min, less than Max;

2, greater than min less than integer.max_value;

3, greater than integer.min_value less than Max

如果我们不使用静态工厂方法,代码一般如下设计:

classrandomintgenerator{/*** Minimum Value*/    Private intMin =Integer.min_value; /*** Maximum Value*/    Private intMax =Integer.max_value; /*** greater than min less than Max *@parammin *@paramMax*/     PublicRandomintgenerator (intMinintmax) {         This. Min =min;  This. Max =Max; }        /*** greater than min less than Integer.max_value*/     PublicRandomintgenerator (intmin) {         This. Min =min; }//Error: Duplicate method randomintgenerator (int) in type Randomintgenerator//    /**//* greater than integer.min_value less than Max//     *///Public randomintgenerator (int max)//    {//This.max = max;//    }}

Observing the above code, we found that the above code is not only readable (new Randomintgenerator (1, 10) and new Randomintgenerator (10), do not look at the document, it is difficult to see the annotation of the object created by the specific meaning of it), And in the design of the last construction method, also reported is wrong, because there is already a consistent working method of the parameter, the hint repeats the definition;

So what happens if we use the static factory method, as shown here:

classrandomintgenerator{/*** Minimum Value*/    Private intMin =Integer.min_value; /*** Maximum Value*/    Private intMax =Integer.max_value; /*** greater than min less than Max *@parammin *@paramMax*/     PublicRandomintgenerator (intMinintmax) {         This. Min =min;  This. Max =Max; }    /*** greater than min less than Max *@parammin *@paramMax*/     Public StaticRandomintgenerator Between (intMinintmax) {        return Newrandomintgenerator (min, max); }    /*** greater than min less than Integer.max_value*/     Public StaticRandomintgenerator Biggerthan (intmin) {        return Newrandomintgenerator (min, integer.max_value); }    /*** greater than integer.min_value less than Max*/     Public StaticRandomintgenerator Smallerthan (intmax) {        return NewRandomintgenerator (Integer.min_value, Max); }}

Successfully meet the requirements: Create three types of RandomIntGenerator objects, and when creating objects, code readability is stronger than the use of construction methods;

2, call, do not need to create a new object every time

The ValueOf method of the Boolean class in the JDK can be a good proof of this advantage, in the Boolean class, there are two pre-created Boolean objects (True,false)

 Public Final classBooleanImplementsjava.io.Serializable, comparable<Boolean>{    /*** The {@codeBoolean} object corresponding to the primitive * value {@codetrue}. */     Public Static FinalBoolean TRUE =NewBoolean (true); /*** The {@codeBoolean} object corresponding to the primitive * value {@codefalse}. */     Public Static FinalBoolean FALSE =NewBoolean (false);

When we call the Boolean.valueof ("true") method, the reference to the two instances is returned, which avoids the creation of unnecessary objects, and if the constructor is used, the effect is not achieved;

     Public Static Boolean valueOf (String s) {        return ToBoolean (s)?  True:false;    }
3. Any subtype object that can return the original return type
    // Reddog and Blackdog as a subclass    of Dog  Public Static Dog getinstance () {        returnnew Reddog ();   or return new Blackdog ();    }
4, the code is more concise
 Packagetmp;classMymap<k,v> {    /**     *     */     PublicMyMap () {} Public Static<K,V> mymap<k,v>newinstance () {return NewMymap<k, v>(); }} Public classmain{ Public Static voidMain (string[] args) {MyMap<string, string> map1 =NewMymap<string, string>(); //more concise, no need to repeat the specified type parameters, you can deduce it yourselfmymap<string, string> map2 =mymap.newinstance (); }}
Disadvantage of using the static factory Method 1, if the class does not contain public or protect construction method, it will not be inherited;

The following classes cannot be inherited by other classes;

class Mymap<k,v> {    /**     *     **    /private  MyMap ()    {    }    publicstatic <K,V> mymap<k,v> newinstance () {         return New Mymap<k, v>();    }}
2, no difference from other ordinary static methods, there is no explicit identification of a static method for instantiating a class

Therefore, generally a static factory method needs to have detailed comments, abide by the standard naming, such as the use of getinstance, ValueOf, Newinstance and other methods name;

Reference from effective Java first article

Consider using static factory methods instead of construction methods

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.