工厂方法+建造者模式的思考

前言

  • 关于两者的使用方法本文不再阐述

  • 关于两者的区别本文不再详细阐述

    讲的优秀的文章随便一搜就可以找的到,但是相同的文章多了就会破坏搜索质量。

  • 选题原因

    在学完工厂方法模式与建造者模式以后,忽然萌生出二者是否可以结合以及如何结合的想法。
    通过实践证实两者可以结合(但并不确定在实际的生产过程中能真正用的上),在实践完成后,再通过网上搜索了相关内容,发现该内容并不多见,找到了一篇关于 该思考的文章
    但是通过比较,发现该文中关于此内容不太合理的地方(仅仅是个人看法,后面的内容会详细说)。

  • 本文通过建造车来展开讨论

实现过程

1.类图 这里写图片描述 2.讲解
类图看起来比较复杂(额,真的尽力了)。
先梳理一下:
AbstractCarModel: 抽象类,是产品[汽车模型]的抽象类,下面的实现类有BenzSCarModel,BMW3CarModel,BMW7CarModel。
AbstractCarBuilder:抽象类,是建造者[汽车生产线]的抽象类,BMWCarBuilder与BenzCarBuilder也是抽象类,继承了AbstractCarBuilder,在这里并没有具体的看出它的作用是什么,但是我们可以在日后进行扩展,比如不同公司的生产线可能存在一些不同,而将此不同写入这个抽象类,而且这样写也会让类之间更加的有层次。
BMW3CarBuilder、BMW7CarBuilder、BenzSCarBuilder分别为建造者具体实现类[具体生产线]。
Factory:工厂接口,BMWCarFactroy、BenzCarFactory为其具体的实现。
Director:指挥者,负责生产方案的预设(生产顺序,生产内容),以及得到具体的Car。
OK,关系梳理完了,下面来具体讲解
AbstractCarModel:上面已经说了它是一个汽车模型,暂时拥有属性[发动机,轮胎,方向盘],还有一个可以判断是否可以跑起来的run()(默认情况下三者都不为空即可判断可以跑起来)。其下的具体实现类BMW3CarModel对run()进行了重写(可以不用发动机也能跑起来)。BMW7CarModel添加了GPS功能。根据能否跑起来来判断是否建车成功。
注意:如果直接new某一个汽车模型,是不能跑起来的,因为需要安装各个部件才能跑起来。
AbstractCarBuilder:建造者[生产线],拥有抽象方法[安装发动机,安装轮胎,安装方向盘],并维护了一个List数组programme,用于存储生产方案,setProgramme()为上层调用,给生产线一个生产方案。start()是按照生产方案的顺序一步一步组装(也就是设置模型的属性不为空)。getModel()是返回model对象。
Factory:工厂,接口内部的方法利用java反射,传入具体的类对象返回该类的对象实例。
注意:这里的工厂生产的是builder,把builder作为工厂的产品。
Director:首先实例化了两种工厂(宝马和奔驰工厂),然后是一个数组来保存生产方案。其他的方法是生产不同的产品。 Director本应属于建造者模式中的一部分,如今却被用到了工厂之上,它原本的作用就是设置生产顺序(即使没有List数组方案),用在工厂之上它的作用也没有发生变化。
Director调用顺序
①拿到工厂实例,创建建造者[具体生产线](需要传入具体生产线的Class对象)
②为List数组programme赋值(制定生产方案),并调用建造者的setProgramme()告诉建造者生产方案。
③调用建造者的start()方法对汽车进行建造。
④调用建造者的getModel()方法获取汽车实例。
⑤返回汽车实例,完成汽车建造。
3.比较
为什么我说 该文章有不合理的地方?
工厂生产产品,只专注于最终得到产品,建造者生产产品关注产品细节,确实没有问题,但是在两种模式的结合之下,工厂生产的产品如果与建造者生产相同的类对象下就会有问题。建造者生产产品的类对象是一个壳子,然后对其一步一步填充,最后得到一个可用的产品(先是一个车模型,然后对车一步一步组装,最后得到车实例)。而如果工厂直接获取产品也只能得到产品的壳子(没有builder的组装,只能得到一个车模型[不能跑起来])。
不能代表谁对谁错,只是不同的思考方式,但我觉得该文作者应该忽略了上面所提到的问题。
4.代码实现

AbstractCarModel

package Model;
public abstract class AbstractCarModel {
    protected String wheel;//轮子
    protected String steeringWheel;//方向盘
    protected String engine;//发动机
    //判断能否跑起来
    public void run(String name) {
        if(wheel==null||steeringWheel==null||engine==null) {
            System.out.println(name+"跑不起来");
        }else {
            System.out.println(name+"跑起来了");
        }
    }
    public String getWheel() {
        return wheel;
    }
    public void setWheel(String wheel) {
        this.wheel = wheel;
    }
    public String getSteeringWheel() {
        return steeringWheel;
    }
    public void setSteeringWheel(String steeringWheel) {
        this.steeringWheel = steeringWheel;
    }
    public String getEngine() {
        return engine;
    }
    public void setEngine(String engine) {
        this.engine = engine;
    };
}

: BenzSCarModel

package Model;
public class BenzSCarModel extends AbstractCarModel{
}

: BMW3CarModel

package Model;
public class BMW3CarModel extends AbstractCarModel{
    @Override
    public void run(String name) {
        if(super.wheel==null||super.steeringWheel==null) {
            System.out.println(name+"跑不起来");
        }else {
            System.out.println(name+"跑起来了");
        }
    }
}

: BMW3CarModel

package Model;
public class BMW7CarModel extends AbstractCarModel{
    private String GPS;
    public String getGPS() {
        return GPS;
    }
    public void setGPS(String gPS) {
        GPS = gPS;
    }
}

: AbstractCarBuilder

package Builder;
import java.util.ArrayList;
import java.util.List;
import Model.AbstractCarModel;
public abstract class AbstractCarBuilder {
    public abstract void installWheel();
    public abstract void installSteeringwheel();
    public abstract void installEngine(String model);
    /**
     * 获取模型
     */
    public abstract AbstractCarModel getModel();
    /**
     * 制定生产方案
     */
    protected List<String> programme=new ArrayList<String>();

    public void setProgramme(List<String> programme) { 
        this.programme=programme; 
    } 
    /**
     * 开始组装
     */
    public void start() {
        for (String part : programme) {
            if(part.equals("wheels")) {
                this.installWheel();
            }else if(part.equals("Steeringwheel")) {
                this.installSteeringwheel();
            }else if(part.matches("engine[A-Z]?")) {
                this.installEngine(part);
            }else{
                System.out.println("没有该组件,请检查方案");
            }
        }
        if(programme.size()==0) {
            System.out.println("请先设置方案");
        }else {
            System.out.println("车辆组装成功");
        }
    }
}

: BenzCarBuilder

package Builder;
public abstract class BenzCarBuilder extends AbstractCarBuilder{
}

: BMWCarBuilder

package Builder;
public abstract class BMWCarBuilder extends AbstractCarBuilder{
}

: BenzSCarBuilder

package Builder;
import Model.AbstractCarModel;
import Model.BenzSCarModel;
public class BenzSCarBuilder extends BenzCarBuilder{
    //先造一个空壳车
    private BenzSCarModel benzCarModel=new BenzSCarModel();
    //下面的方法都是填充空壳车
    @Override
    public void installWheel() {
        benzCarModel.setWheel("我有轮子了");
        System.out.println("奔驰S级车安装了轮子");
    }
    @Override
    public void installSteeringwheel() {
        benzCarModel.setSteeringWheel("我有轮子了");
        System.out.println("奔驰车S级车安装了方向盘");
    }
    @Override
    public void installEngine(String model) {
        benzCarModel.setEngine("我有发动机"+model);
        System.out.println("奔驰车S级车安装了"+model);
    }
    //返回该车模型
    @Override
    public AbstractCarModel getModel() {
        return benzCarModel;
    }
}

: BMW3CarBuilder

package Builder;
import Model.BMW3CarModel;
import Model.AbstractCarModel;
public class BMW3CarBuilder extends BMWCarBuilder{
    private BMW3CarModel bmw3CarModel=new BMW3CarModel();
    @Override
    public AbstractCarModel getModel() {
        return bmw3CarModel;
    }
    @Override
    public void installWheel() {
        bmw3CarModel.setWheel("我有轮子了");
        System.out.println("宝马3系车安装了轮子");
    }
    @Override
    public void installSteeringwheel() {
        bmw3CarModel.setSteeringWheel("我有方向盘了");
        System.out.println("宝马3系车安装了方向盘");

    }
    @Override
    public void installEngine(String model) {
        bmw3CarModel.setEngine("我有发动机"+model);
        System.out.println("宝马3系车安装了"+model);
    }
}

: BMW7CarBuilder

package Builder;
import Model.AbstractCarModel;
import Model.BMW7CarModel;
public class BMW7CarBuilder extends BMWCarBuilder{
    private BMW7CarModel bmw7CarModel=new BMW7CarModel();
    @Override
    public AbstractCarModel getModel() {
        return bmw7CarModel;
    }
    @Override
    public void installWheel() {
        bmw7CarModel.setWheel("我有轮子了");
        System.out.println("宝马7系车安装了轮子");
    }
    @Override
    public void installSteeringwheel() {
        bmw7CarModel.setSteeringWheel("我有方向盘了");
        System.out.println("宝马7系车安装了方向盘");

    }
    @Override
    public void installEngine(String model) {
        bmw7CarModel.setEngine("我有发动机"+model);
        System.out.println("宝马7系车安装了"+model);
    }
    public void installGPS() {
        bmw7CarModel.setGPS("我有GPS了");
        System.out.println("宝马7系车安装了GPS");
    }
    @Override
    public void start() {
        for (String part : super.programme) {
            if(part.equals("wheels")) {
                this.installWheel();
            }else if(part.equals("Steeringwheel")) {
                this.installSteeringwheel();
            }else if(part.matches("engine[A-Z]?")) {
                this.installEngine(part);
            }else if(part.matches("GPS")){
                this.installGPS();
            }else {
                System.out.println("没有该组件,请检查方案");
            }
        }
        if(programme.size()==0) {
            System.out.println("请先设置方案");
        }else {
            System.out.println("车辆组装成功");
        }
    }
}

: Factory

package Factory;
import Builder.AbstractCarBuilder;
public interface Factory {
    //根据传入的Class对象返回对应的实例
    public AbstractCarBuilder createBuilder(Class<?> c);
}

: BenzCarFactory

package Factory;
import Builder.AbstractCarBuilder;
import Builder.BenzCarBuilder;
public class BenzCarFactory implements Factory{
    @Override
    public AbstractCarBuilder createBuilder(Class<?> c) {
        AbstractCarBuilder benzCarBuilder=null;
        try {
            benzCarBuilder= (BenzCarBuilder) Class.forName(c.getName()).newInstance();
        } catch (Exception e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } 
        return  benzCarBuilder;
    }
}

: BMWCarFactroy

package Factory;
import Builder.BMWCarBuilder;
import Builder.AbstractCarBuilder;
public class BMWCarFactroy implements Factory{
    @Override
    AbstractCarBuilder bmwCarBuild=null;
        try {
            bmwCarBuild=(BMWCarBuilder) Class.forName(c.getName()).newInstance();
        } catch (Exception e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } 
        return bmwCarBuild;
    }

}

: Director

package main;
import java.util.ArrayList;
import java.util.List;
import Builder.BMW3CarBuilder;
import Builder.BMW7CarBuilder;
import Builder.BenzSCarBuilder;
import Builder.AbstractCarBuilder;
import Factory.BMWCarFactroy;
import Factory.BenzCarFactory;
import Factory.Factory;
import Model.BMW3CarModel;
import Model.BMW7CarModel;
import Model.BenzSCarModel;
public class Director {
    //生产方案
    private List<String> programme=new ArrayList<String>();
    //宝马工厂
    private Factory bmwFactory=new BMWCarFactroy();
    //奔驰工厂
    private Factory benzFactory=new BenzCarFactory();
    public Director() {
        this.getHighBMW3CarModel();
        this.getLowBMW3CarModel();
        BMW7CarModel bmw7CarModel=this.getBMW7CarModel();
        System.out.println("--------------");
        BenzSCarModel benzSCarModel=this.getBenzSCarModel();
        System.out.println("--------------");
        bmw7CarModel.run("bmw7Car");
        System.out.println("--------------");
        benzSCarModel.run("benzSCar");
    }
    //生产高端宝马3
    public BMW3CarModel getHighBMW3CarModel() {
        //采用最好发动机的宝马3系高端车
        //设置生产方案
        programme.clear();
        programme.add("wheels");
        programme.add("Steeringwheel"); 
        programme.add("engineA");
        //获取对应的builder对象
        AbstractCarBuilder bmw3carBuilder=bmwFactory.createBuilder(BMW3CarBuilder.class);
        //将方案设置给建造者
        bmw3carBuilder.setProgramme(programme);
        BMW3CarModel bmw3CarModel=(BMW3CarModel) bmw3carBuilder.getModel();
        //组装前尝试运行
        bmw3CarModel.run("HighBMW3Car");
        bmw3carBuilder.start();//组装
        bmw3CarModel.run("HighBMW3Car");//组装后再次运行
        System.out.println("--------------");
        return bmw3CarModel;
    }
    //生产低端宝马3
    public BMW3CarModel getLowBMW3CarModel() {
        //没有发动机的宝马3系低端车
        programme.clear();
        programme.add("wheels");
        programme.add("Steeringwheel"); 
        AbstractCarBuilder bmw3carBuilder=bmwFactory.createBuilder(BMW3CarBuilder.class);
        bmw3carBuilder.setProgramme(programme);
        bmw3carBuilder.start();
        BMW3CarModel bmw3LowCarModel=(BMW3CarModel) bmw3carBuilder.getModel();
        bmw3LowCarModel.run("bmw3LowCar");
        System.out.println("--------------");
        return (BMW3CarModel)bmw3LowCarModel;
    }
    //生产BMW7
    public BMW7CarModel getBMW7CarModel() {
        programme.clear();
        programme.add("wheels");
        programme.add("Steeringwheel"); 
        programme.add("engineB");
        programme.add("GPS");
        AbstractCarBuilder bmw7carBuilder=bmwFactory.createBuilder(BMW7CarBuilder.class);
        bmw7carBuilder.setProgramme(programme);
        bmw7carBuilder.start();
        return (BMW7CarModel)bmw7carBuilder.getModel();
    }
    //生产奔驰S  
    public BenzSCarModel getBenzSCarModel() {
        programme.clear();
        programme.add("engineC");
        programme.add("wheels");
        programme.add("Steeringwheel"); 
        AbstractCarBuilder benzScarBuilder=benzFactory.createBuilder(BenzSCarBuilder.class);
        benzScarBuilder.setProgramme(programme);
        benzScarBuilder.start();
        return (BenzSCarModel)benzScarBuilder.getModel();
    }
}

The more I share, the more I have.
如有建议或错误,欢迎指正。联系方式h1096938190@163.com.
I love technology.And you?

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

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值