因为静态工厂和构造器有个共同的局限性:它们都不能很好地扩展到大量的可选参数。所以咱们下面要来讲说构建器,所谓的构建器其实就是具备建立外部类功能的内部静态类。首先咱们先理解几个模式java
1.重叠构造器模式安全
提供一个只有必要参数的构造器,第二个构造器有一个可选参数,第三个构造器有两个可选参数,依次类推,直到最后一个构造器包含全部的可选参数。多线程
缺点:谁做为第一个可选参数是一个问题,由于后一个包含两个可选参数的构造器必须传递值给第一个可选参数,致使须要设置许多本不想设置的参数。并发
2.JavaBean模式高并发
经过一个无参构造器建立对象,而后调用setter方法来设置每一个必要的参数。这样建立实例很容易,产生的代码读起来也比较容易,由于经过setter的方法名能知道设置的参数是哪个。ui
缺点:构造过程被分到了几个调用之中,在构造过程当中没法保证JavaBean的一致性。this
3.Builder模式(本条主要)spa
不直接生成想要的对象,而是让客户利用全部必要的参数调用构造器,获得一个builder对象,而后客户端在builder对象上调用相似于setter的方法设置每一个可选参数,最后,客户端调用无参的build方法来生成不可变的对象。线程
好了,下面就让咱们来看看具体的构建器的作法:设计
public class BuilderObject { private final String filed01; private final String filed02; private final String filed03; private final String filed04; private BuilderObject(Builder builder){ this.filed01 = builder.filed01; this.filed02 = builder.filed02; this.filed03 = builder.filed03; this.filed04 = builder.filed04; } //构建器(内部类) public static class Builder{ private String filed01; private String filed02; private String filed03; private String filed04; public Builder filed01(String filed01){ this.filed01 = filed01; return this; } public Builder filed02(String filed02){ this.filed02 = filed02; return this; } public Builder filed03(String filed03){ this.filed03 = filed03; return this; } public Builder filed04(String filed04){ this.filed04 = filed04; return this; } public BuilderObject build(){//build方法,生成一个须要被构建的类 return new BuilderObject(this); } } }
使用的时候咱们只须要按照本身的意愿来添加便可:
BuilderObject builderObject = new BuilderObject.Builder() .filed01("filed01") .filed02("filed02") .filed03("filed03") .filed04("filed04") .build();
那咱们应该在何时使用构建器呢?若是有一个类有不少个参数filed0一、filed0二、filed0三、filed0四、filed0五、filed06......其中有些必填有些非必填。这时候咱们若是选择构造器(咱们少选点参数来举例,就选择filed0一、filed0二、filed03,其中就filed01必填,另外两个选填)的话,就以下:
public MyObject(String filed01, String filed02, String field03) { this.filed01 = filed01; this.filed02 = filed02; this.field03 = field03; } public MyObject(String filed01, String filed02) { this(filed01, filed02, null); } public MyObject(String filed01) { this(filed01, null, null); }
那么若是有更多的参数就须要更多的构造方法了,显然很不科学。同理静态工厂方法也是不合理的,这时候有人可能会说,用Javabean方式不就能够了么?给每一个属性设置setter/getter方法,看似好像这种方法好像解决了上述问题,可是!javabean模式有一个致命的缺陷,就是它的构造过程分部到几回调用中,而不是一次性完成的。也就是说三个字段我须要使用三次setter方法,而不是一次性完成。这意味着什么呢?意味着它有可能在构造的过程当中被改变,这一点在多线程、高并发的程序中显得尤其重要。不只如此,javabean模式还有第二个缺点:若是对象中含有final修饰的字段,那么javabean模式将不能对其执行setter操做。
总结:
若是类的构造器或是静态工厂方法中具备多个参数,设计这种类时,使用Builder方式(构建器方式)就是种不错的选择,特别是当大可能是参数都是可选的时候。与使用传统的重叠构造器模式相比,使用Builder模式的客户端代码将更容易阅读和编写,构建器也比javabean更加安全。