• 构造者模式


    一 适用场景产品类非常复杂或者产品类中的调用顺序不同产生不同的结果。比如说,现在有个场景:客户公司让我们按一定的条件生产汽车模型,这个条件是,这些汽车模型可以按照用户自己给定的任意操作顺序来运行,针对这个问题该怎么解决呢?

    二 实现方式:

    创建产品抽象类CarModel:

    /**
     * @author chenyk
     * @date 2018年9月6日
     * 产品抽象类
     */
    
    public abstract class CarModel {
        
        // 各个基本方法的执行顺序就定义在这个集合中
        private List<String> sequence = new ArrayList<String>();
        
        // 开始启动
        public abstract void start();
        
        //停止
        public abstract void stop();
        
        // 喇叭声音
        public abstract void alarm();
        
        // 引擎启动声音
        public abstract void engineBoom();
        
        // 根据定义好的顺序决定哪个先执行
        public void run(){
            for(int i=0;i<this.sequence.size();i++){
                String actionName = this.sequence.get(i);
                if(actionName.equals("start")){
                    this.start();
                }else if(actionName.equals("stop")){
                    this.stop();
                }else if(actionName.equals("alarm")){
                    this.alarm();
                }else if(actionName.equals("engineBoom")){
                    this.engineBoom();
                }
            }
        }
        
        public void setSequence(List<String> sequence){
            this.sequence = sequence;
        }
        
        
    }

    创建产品类BenzModel和BMWModel:

    /** 
     * @author chenyk
     * @date 2018年9月6日
     * 具体产品类
     */
    
    public class BenzModel extends CarModel{
    
        @Override
        public void start() {
            System.out.println("奔驰开始启动");
        }
    
        @Override
        public void stop() {
            System.out.println("奔驰停止");
        }
    
        @Override
        public void alarm() {
            System.out.println("奔驰的喇叭声音");
        }
    
        @Override
        public void engineBoom() {
            System.out.println("奔驰的引擎启动声音");
        }
    
    }
    /** 
     * @author chenyk
     * @date 2018年9月6日
     * 具体产品类
     */
    
    public class BMWModel extends CarModel{
    
        @Override
        public void start() {
            System.out.println("宝马开始启动");
        }
    
        @Override
        public void stop() {
            System.out.println("宝马停止");
        }
    
        @Override
        public void alarm() {
            System.out.println("宝马的喇叭声音");
        }
    
        @Override
        public void engineBoom() {
            System.out.println("宝马的引擎启动声音");
        }
    
    }

    创建构造者抽象类

    public abstract class CarBuilder {
        
        public abstract void setSequence(ArrayList<String> sequence);
        
        public abstract CarModel getCarModel();
        
    }

    创建构造者具体类

    public class BenzBuilder extends CarBuilder{
    
        private BenzModel benzModel = new BenzModel();
        
        @Override
        public void setSequence(ArrayList<String> sequence) {
            this.benzModel.setSequence(sequence);
        }
    
        @Override
        public CarModel getCarModel() {
            return this.benzModel;
        }
    
    }
    public class BMWBuilder extends CarBuilder{
    
        private BMWModel bmw = new BMWModel();
        
        @Override
        public void setSequence(ArrayList<String> sequence) {
            this.bmw.setSequence(sequence);
        }
        
        @Override
        public CarModel getCarModel() {
            return this.bmw;
        }
    
    }

    创建导演类:

    /**
     * @author chenyk
     * @date 2018年9月6日
     * 导演类
     */
    
    public class Director {
        
        private ArrayList<String> sequence = new ArrayList<String>();
        
        private BenzBuilder benzBuilder = new BenzBuilder();
        
        private BMWBuilder bmwBuilder = new BMWBuilder();
        
        /**
         * A类型奔驰模型:start----》stop
         * @return
         */
        public BenzModel getABenzModel(){
            this.sequence.clear();
            this.sequence.add("start");
            this.sequence.add("stop");
            this.benzBuilder.setSequence(this.sequence);
            return (BenzModel) this.benzBuilder.getCarModel();
        }
        
        /**
         * B类型奔驰模型:start---》engineBoom---》stop
         * @return
         */
        public BenzModel getBBenzModel(){
            this.sequence.clear();
            this.sequence.add("start");
            this.sequence.add("engineBoom");
            this.sequence.add("stop");
            this.benzBuilder.setSequence(this.sequence);
            return (BenzModel) this.benzBuilder.getCarModel();
        }
        
        
        /**
         * C类型宝马模型:start---》alarm
         * @return
         */
        public BMWModel getCBMWModel(){
            this.sequence.clear();
            this.sequence.add("start");
            this.sequence.add("alarm");
            this.bmwBuilder.setSequence(this.sequence);
            return (BMWModel) this.bmwBuilder.getCarModel();
        }
        
        
        /**
         * D类型宝马模型:start---》stop
         * @return
         */
        public BMWModel getDBMWModel(){
            this.sequence.clear();
            this.sequence.add("start");
            this.sequence.add("stop");
            this.bmwBuilder.setSequence(this.sequence);
            return (BMWModel) this.bmwBuilder.getCarModel();
        }
        
        
    }

    创建场景类Client:

    public class Client {
        public static void main(String[] args) {
            Director director = new Director();
            
            //10辆A类型奔弛
            for(int i=0;i<10;i++){
                director.getABenzModel().run();
            }
            
            //10辆D类型宝马
            for (int i = 0; i < 10; i++) {
                director.getDBMWModel().run();
            }
            
        }
    }

    总结:对于构造者模式,有这几个角色:

    导演类Director,负责安排运行顺序,然后告诉构造者开始建造。

    建造者 CarBuilder和BMWBuilder,BenzBuilder,按照指定的顺序建造奔弛和宝马的车模型。

    产品类 CarModel和BenzModel,BMWModel,就是建造者生产出的车模型,具体的产品。

    通过这三个角色,我们可以建造出不同车型各种运行顺序的车模型,可以按照想要的顺序进行各种组合,这就是构造者模型的最大特点。

    参考资料:《设计模式之禅》

  • 相关阅读:
    MySql面试题、知识汇总、牛客网SQL专题练习
    产生过拟合的原因
    《人类简史》这本烧脑书风靡全球的秘密是什么?
    厌食?暴食?试试这个 VR 新疗法
    协程、异步IO
    进程池
    进程(同步)锁
    特朗普变脸:同媒体“友好会谈”,怨媒体“死不悔改”
    多进程Queue
    redis 在 php 中的应用(事务 [ Transaction ] 篇)
  • 原文地址:https://www.cnblogs.com/51life/p/9598723.html
Copyright © 2020-2023  润新知