什么是建造者模式,建造者模式用一句话来说,就是把一个复杂对象,简单化的创建(我的理解,不喜勿喷)
建造者模式包含部分有:
一个复杂对象: Object
一个基类建造器: Builder && (BuilderChildren1、BuilderChildren2、...、BuilderChildrenN)
一个指挥类: Direction
举个例子来说,假如
复杂对象 ==> Car
Builder ==> BaseFactoryBuilder生产汽车的厂家 (1...n 有n个厂家)
Direction ==> 指挥生产汽车机器(控制生成汽车步骤)
汽车类:
/**
* 汽车类
* 举例:定义2个够了,不要在意这些细节
*/
class Car {
/**
* 轮子
*/
lateinit var wheel: Any
/**
* 发动机
*/
lateinit var Engine: Any
}
工厂类:
/**
* 基础工厂建造器
* 职责:主要负责生产出一辆汽车
*/
abstract class BaseFactoryBuilder {
protected var car: Car = Car()
var wheel: Any = "空轮子"
var engine: Any = "空引擎"
/**
* 建造轮子
*/
abstract fun buildWheel()
/**
* 建造引擎
*/
abstract fun buildEngine()
/**
* 获得一个完整的汽车
*/
fun getWholeCar() = car
}
/**
* 宝马工厂
*/
class BMWFactory : BaseFactoryBuilder() {
override fun buildEngine() {
this.wheel = "我是宝马引擎"
}
override fun buildWheel() {
this.wheel = "我是宝马轮子"
}
}
指挥类:
/**
* 指挥类
* 一般装载汽车都是自动化的话,所以就用机器了
*/
class Machine {
lateinit var factoryBuilder: BaseFactoryBuilder;
fun construct(): Car {
factoryBuilder.buildWheel() // 我装装装轮子
factoryBuilder.buildEngine() // 我装装装引擎
return factoryBuilder.getWholeCar() // 获得这个车子
}
}
所有东西准备好,接下来干什么呢,就是让顾客(main)去要车
fun main(args: Array<String>) {
var factoryBuilder = BMWFactory()
var machine = Machine()
machine.factoryBuilder = factoryBuilder
var car: Car = machine.construct()
}
然后大概就是这样的一个原理,有人问,这不是构造函数也可以吗,没错构造函数也可以实现,但是会有以下问题
(1) 经常对象是类型是一致的(假设成员属性都是Object),构造函数要怎么识别,识别那个,并且要在对应位置填入参数
(2) 有时,我只想有条件的输入某些参数(我就是这么傲娇),其他用默认值,那在Java中要对每个参数来进行一个构造函数,还有参数综合进行分组...如果有几百个成员属性,想想就头痛
/*----------------------- 虽然kotlin都可以实现,别打岔 ------------------------------------------------------------- */
(3) 有时,属性与属性之间是有关系的,比如 车底盘 和 车轮廓 ,你要先装车底盘,才能把 车轮廓放上去
以上问题,你需要获得Car,你要去查找Car源码,你才能正确的创建一个Car
相反地,利用观察者模式,可以轻松解决以上三个问题
/*--------------------- 在引入一个额外的 ---------------------------- */
通常制作简单一个Builder类的时候,会把 Direction类 和 builder类 合并起来,例如 OkHttp 的 Request对象,把以上对象合并的,可以简单化
// BaseFactoryBuilder类中
fun getWholeCar(): Car {
buildWheel() // 我装装装轮子
buildEngine() // 我装装装引擎
return getWholeCar() // 获得这个车子
}
// 在main函数使用
fun main(args: Array<String>) {
var car: Car = BMWFactory().getWholeCar()
}