Android常用设计模式之Builder模式理解

Android常用设计模式之Builder模式

1 单例模式

单例模式之前有详细的介绍,可移步到链接: 常见的单例模式及其特点

2 Builder模式

什么是Builder模式?
将一个复杂对象的构建与它的表示分离,使得同样的构建过程可以创建不同的表示。但是用文字表示出来还是很抽象,想要真正的了解Builde模式最好的方式还是通过样例代码来看。
下面我们通过一个例子来揭开Builder模式的面纱。
我有一个Student类,这个类有name、age、sex、score四个属性。

/**
 * Created by yangyang on 2022/9/30.
 */
public class Student {
    private String name;
    private int age;
    private int sex;
    private double score;

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        this.age = age;
    }

    public int getSex() {
        return sex;
    }

    public void setSex(int sex) {
        this.sex = sex;
    }

    public double getScore() {
        return score;
    }

    public void setScore(double score) {
        this.score = score;
    }
}

通常为了方便定义会定义一个构造方法

    public Student(String name, int age, int sex, double score) {
        this.name = name;
        this.age = age;
        this.sex = sex;
        this.score = score;
    }

或者有时候我们需要一个空的构造函数

    public Student() {

    }

或者只想传部分构造函数

  public Student(String name) {
        this.name = name;
    }
    
 public Student(String name, double score) {
        this.name = name;
        this.score = score;
    }
    
  public Student(String name, int age, double score) {
        this.name = name;
        this.age = age;
        this.score = score;
    }

根据需要创建对象

Student stu1=new Student(); 
Student stu2=new Student("诺克萨斯之手"); 
Student stu3=new Student("厄运小姐",100); 
Student stu4=new Student("卡莎",18,100); 
Student stu5=new Student("卡特琳",18,1,100);

需要几个参数的构造函数我们就要在Student去定义,所以不是很简便,只看传入的参数我们也不好猜测各个参数具体意思。可读性较差,所以就有了Builder模式

/**
 * Created by yangyang on 2022/9/30.
 */
public class Student {
    private String name;
    private int age;
    private int sex;
    private double score;

    private Student(Builder builder) {
        this.name = builder.name;
        this.age = builder.age;
        this.sex = builder.sex;
        this.score = builder.score;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        this.age = age;
    }

    public int getSex() {
        return sex;
    }

    public void setSex(int sex) {
        this.sex = sex;
    }

    public double getScore() {
        return score;
    }

    public void setScore(double score) {
        this.score = score;
    }

    static class Builder {
        private String name;
        private int age;
        private int sex;
        private double score;

        public Builder name(String name) {
            this.name = name;
            return this;
        }

        public Builder age(int age) {
            this.age = age;
            return this;
        }

        public Builder sex(int sex) {
            this.sex = sex;
            return this;
        }

        public Builder score(double score) {
            this.score = score;
            return this;
        }

        public Student build() {
            return new Student(this);
        }
    }
}

Student 类里增加了一个静态内部类Builder 并且跟Student 类成员变量一致,然后通过Builder里的成员函数来为Student属性赋值。
根据需要创建对象

Student.Builder builder=new Student.Builder();
Student student=builder.name("卡特琳").age(18).sex(1).score(100) .build();

可以看出大大提高了代码的可读性,每个参数可以通过builder.的方式设置,属性的意思也一目了然。

Builder模式的应用场景

上一篇文章我们说到OkHttp,Builder模式在OkHttp中得到了应用。

通过Builder构建一个OkHttpClient

  constructor() : this(Builder())
  init {
    if (connectionSpecs.none { it.isTls }) {
      this.sslSocketFactoryOrNull = null
      this.certificateChainCleaner = null
      this.x509TrustManager = null
      this.certificatePinner = CertificatePinner.DEFAULT
    } else if (builder.sslSocketFactoryOrNull != null) {
      this.sslSocketFactoryOrNull = builder.sslSocketFactoryOrNull
      this.certificateChainCleaner = builder.certificateChainCleaner!!
      this.x509TrustManager = builder.x509TrustManagerOrNull!!
      this.certificatePinner = builder.certificatePinner
          .withCertificateChainCleaner(certificateChainCleaner!!)
    } else {
      this.x509TrustManager = Platform.get().platformTrustManager()
      this.sslSocketFactoryOrNull = Platform.get().newSslSocketFactory(x509TrustManager!!)
      this.certificateChainCleaner = CertificateChainCleaner.get(x509TrustManager!!)
      this.certificatePinner = builder.certificatePinner
          .withCertificateChainCleaner(certificateChainCleaner!!)
    }

    verifyClientState()
  }

默认的Builder

 class Builder constructor() {
    internal var dispatcher: Dispatcher = Dispatcher()
    internal var connectionPool: ConnectionPool = ConnectionPool()
    internal val interceptors: MutableList<Interceptor> = mutableListOf()
    internal val networkInterceptors: MutableList<Interceptor> = mutableListOf()
    internal var eventListenerFactory: EventListener.Factory = EventListener.NONE.asFactory()
    internal var retryOnConnectionFailure = true
    internal var authenticator: Authenticator = Authenticator.NONE
    internal var followRedirects = true
    internal var followSslRedirects = true
    internal var cookieJar: CookieJar = CookieJar.NO_COOKIES
    internal var cache: Cache? = null
    internal var dns: Dns = Dns.SYSTEM
    internal var proxy: Proxy? = null
    internal var proxySelector: ProxySelector? = null
    internal var proxyAuthenticator: Authenticator = Authenticator.NONE
    internal var socketFactory: SocketFactory = SocketFactory.getDefault()
    internal var sslSocketFactoryOrNull: SSLSocketFactory? = null
    internal var x509TrustManagerOrNull: X509TrustManager? = null
    internal var connectionSpecs: List<ConnectionSpec> = DEFAULT_CONNECTION_SPECS
    internal var protocols: List<Protocol> = DEFAULT_PROTOCOLS
    internal var hostnameVerifier: HostnameVerifier = OkHostnameVerifier
    internal var certificatePinner: CertificatePinner = CertificatePinner.DEFAULT
    internal var certificateChainCleaner: CertificateChainCleaner? = null
    internal var callTimeout = 0
    internal var connectTimeout = 10_000
    internal var readTimeout = 10_000
    internal var writeTimeout = 10_000
    internal var pingInterval = 0
    internal var minWebSocketMessageToCompress = RealWebSocket.DEFAULT_MINIMUM_DEFLATE_SIZE
    internal var routeDatabase: RouteDatabase? = null
    ...
    }

使用

   OkHttpClient.Builder okHttpClient = new OkHttpClient.Builder();
        okHttpClient.readTimeout(mReadTimeOut, TimeUnit.MILLISECONDS);
        okHttpClient.connectTimeout(mConnectTimeOut, TimeUnit.MILLISECONDS);
        okHttpClient.writeTimeout(mWriteTimeOut, TimeUnit.MILLISECONDS);
        // 默认开启请求的打印信息数据,在每次发布版本的时候可以手动关闭
        if (mIsIntercept) {
            okHttpClient.addInterceptor(new HttpRequestInterceptor());
        }

还有就是在AlertDialog应用比较多
在这里插入图片描述

1、私有化构建方法,使其只能通过内部类Builder的build方法创建。
2、静态内部类作为桥梁,可以设置所有参数。
3、通过build的方法创建Student实例。
4、由于Builder这个桥梁,使得构建时可以设置不同参数,把构建和参数解耦。
5、创建实例后,参数不可再改。
6、链式调用代码清晰。

总结

整体来说Builder模式比较简单,其核心就是隐藏构造方法,通过一个静态内部类封装构造。隐藏构建过程。主要使用于对象比较复杂的时候

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值