• 工厂模式


    1.定义

    定义一个创建对象的接口,由子类决定实例化的类是哪一个,工厂方法把类的实例化推迟到子类.

    注意:虽然简单工厂模式平常用的很多,但是它更像是一个编程习惯而并不是一个设计模式,工厂模式主要包括工厂模式和抽象工厂模式.

    2.代码实现

    还是以pizza为例子,上个简单工厂模式中说到了有四种披萨,分别是:芝士披萨,花甲披萨,意式香肠披萨,蔬菜披萨.

    假如不同地区生产的pizza不一样,比如有:

    纽约芝士披萨,纽约花甲披萨,纽约意式香肠披萨,纽约蔬菜披萨

    或者是

    芝加哥芝士披萨,芝加哥花甲披萨,芝加哥意式香肠披萨,芝加哥纽约蔬菜披萨.

    这些披萨的实现类如下:

    定义抽象披萨类

    public abstract class Pizza {
        String name;
        String dough;
        String sauce;
        ArrayList toppings = new ArrayList();
        public void prepare() {
            System.out.println("Prepare:"+name);
            System.out.println(toppings);
        }
        public void bake() {
            System.out.println("bake:"+name);
        }
        public void cut() {
            System.out.println("cut:"+name);
        }
        public void box() {
            System.out.println("box:"+name);
        }
        public String getName() {
            return name;
        }
    }

    纽约四种披萨:

    public class NYStyleCheesePizza extends Pizza {
    
        public NYStyleCheesePizza() {
            name = "NY Style Sauce and Cheese Pizza";
            dough = "Thin Crust Dough";
            sauce = "Marinara Sauce";
            toppings.add("Grated Reggiano Cheese");
        }
        
    }
    public class NYStyleClamPizza extends Pizza {
    
    }
    public class NYStylePepperoniPizza extends Pizza {
    
    }
    public class NYStyleVeggiePizza extends Pizza {
    
    }

    芝加哥四种披萨:

    public class ChicagoStyleCheesePizza extends Pizza {
    
        public ChicagoStyleCheesePizza() {
            name = "Chicago Style Deep and Cheese Pizza";
            dough = "Extra Thick Crust Dough";
            sauce = "Plum Tomato Sauce";
            toppings.add("Shredded Mozzarella Cheese");
        }
        
        public void cut() {
            System.out.println("Cutting the pizza into square slices");
        }
        
    }
    public class ChicagoStyleClamPizza extends Pizza {
    
    }
    public class ChicagoStylePepperoniPizza extends Pizza {
    
    }
    public class ChicagoStyleVeggiePizza extends Pizza {
    
    }

    虽然简单工厂可以创建不同的工厂类来生成,但是这些工厂类在传入Store后只能生成一种地区的pizza,如果要生成别的地区的pizza还要重新传入工厂类.

    这里我们用改进后的工厂模式实现.

    定义抽象披萨商店类,这边和简单工厂模式不同的是定义成了抽象类,因为需要子类来决定具体生产哪一种披萨

    public abstract class PizzaStore {
        
        public PizzaStore() {}
    
        
        public Pizza orderPizza(String type) {
            Pizza pizza;
            pizza = createPizza(type);
            pizza.prepare();
            pizza.bake();
            pizza.cut();
            pizza.box();
            return pizza;
        }
        /**
         * 让子类决定生成哪一种披萨
         * @param type 参数类型
         * @return 披萨
         */
        abstract Pizza createPizza(String type);
    }

    定义纽约披萨商店和芝加哥披萨商店

    public class NYStylePizzaStore extends PizzaStore {
        
        public NYStylePizzaStore() {
            super();
        }
    
    
        @Override
        Pizza createPizza(String type) {
            if (type.equals("cheese")) {
                return new NYStyleCheesePizza();
            } else if (type.equals("pepperoni")) {
                return new NYStylePepperoniPizza();
            } else if (type.equals("veggie")) {
                return new NYStyleVeggiePizza();
            } else if (type.equals("clam")) {
                return new NYStyleClamPizza();
            }
            return null;
        }
    
    }
    public class ChicagoStylePizzaStore extends PizzaStore {
    
    
        @Override
        Pizza createPizza(String type) {
            if (type.equals("cheese")) {
                return new ChicagoStyleCheesePizza();
            } else if (type.equals("pepperoni")) {
                return new ChicagoStylePepperoniPizza();
            } else if (type.equals("veggie")) {
                return new ChicagoStyleVeggiePizza();
            } else if (type.equals("clam")) {
                return new ChicagoStyleClamPizza();
            }
            return null;
        }
    
    }

    定义测试类并进行测试

    public class PizzaTest {
         public static void main(String[] args) {
             PizzaStore nyPizzaStore = new NYStylePizzaStore();
             PizzaStore chicagoStore = new ChicagoStylePizzaStore();
             
             Pizza pizza = nyPizzaStore.orderPizza("cheese");
             System.out.println();
             pizza = chicagoStore.orderPizza("cheese");
             /*
                  输出如下:
                Prepare:NY Style Sauce and Cheese Pizza
                [Grated Reggiano Cheese]
                bake:NY Style Sauce and Cheese Pizza
                cut:NY Style Sauce and Cheese Pizza
                box:NY Style Sauce and Cheese Pizza
                
                Prepare:Chicago Style Deep and Cheese Pizza
                [Shredded Mozzarella Cheese]
                bake:Chicago Style Deep and Cheese Pizza
                Cutting the pizza into square slices
                box:Chicago Style Deep and Cheese Pizza
              */
        }
    }

    3.总结

    可以看到工厂模式最主要的特点就是子类决定生成哪一种披萨,虽然和简单工厂模式有点像,if  else 挺多的,但是子类来做决定的话弹性更高一点,而且也更直观理解要生成什么对象.

    虽然工厂模式避免不了用new关键字创建类,但是它把类的创建都归并到一起了,便于管理.

    反射也可以创建类,spring就是通过反射来实现ioc的.

  • 相关阅读:
    [ML] the notes
    [Java] 在 jar 文件中读取 resources 目录下的文件
    [LeetCode] 53. Maximum Subarray 解题思路
    [git] git 分支管理和工作流程
    debug实战:Unmanaged High Memory非托管高内存
    batch insert 1 million datas into mysql
    nuget的小Tips
    debug实战:进程Hang+High CPU
    debug实战:COM组件GetToSTA导致高内存+GC被阻塞
    svn cleanup failed问题解决
  • 原文地址:https://www.cnblogs.com/lishuaiqi/p/11116044.html
Copyright © 2020-2023  润新知