工厂模式&抽象工厂——HeadFirst设计模式学习笔记
Posted HectorHou
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了工厂模式&抽象工厂——HeadFirst设计模式学习笔记相关的知识,希望对你有一定的参考价值。
当使用new实例化一个类时,使用的是实现,而不是接口,代码捆绑着具体类会导致代码更脆弱缺乏弹性,使用松耦合的OO模式可以得到解脱。
工厂:封装对象的创建,处理创建对象的细节
静态工厂:利用静态方法定义一个简单的工厂。优点:不需要创建工厂类的实例化。缺点:不能通过继承改变创建方法行为。
简单工厂:简单工厂并不是一种设计模式,因为只是简单的把创建对象的代码封装起来
工厂模式:在父类定义了一个创建对象的接口,通过让子类决定创建的对象是什么,来达到让对象创建的过程封装的目的。工厂方法让类把实例化推迟到子类
抽象工厂:提供一个接口,用于创建相关或依赖对象的家族,而不需要指明具体的类
特点:
- 工厂方法用来处理对象的创建,并将这样的行为封装在子类中。这样客户程序中超类的代码就和子类对象的创建部分解耦了
- 简单工厂vs工厂模式:简单工厂把全部的事情在一个地方做完了,而工厂模式是一个创建框架,让子类决定如何实现
- 抽象工厂vs工厂模式
- 抽象工厂的方法经常以工厂方法的方式实现,抽象工厂的任务是定义一个负责创建一组产品的接口
- 工厂方法使用继承,抽象工厂使用组合
- 工厂方法只是用来创建一种产品,而抽象工厂创建的是一个产品家族
- 使用工厂模式意味着需要扩展一个类并覆盖它的工厂方法。抽象工厂提供了一个创建产品家族的抽象类型,类型的子类定义了产品生产的方式
设计原则:
- 依赖倒置原则:要依赖抽象,不要依赖具体类。高层次的模块不应该依赖于低层次的模块,他们都应该依赖于抽象。抽象不应该依赖于具体实现,具体实现应该依赖于抽象。(http://baike.baidu.com/link?url=mYRSYyXnTF-kbBdpEpLn53DrmxWb2QJBIIbxS4PA5IkqKJQolObBS8fzAXU81mOX962UcGuwwY6UOlAUavEX1WFQdJY7Xg96ezG7vj-Ss_y_8R_fCiSmSGN-DMM6XSroAmE6sKIFiSSBXJIOBl7cca)
- 变量不要持有具体类的引用
- 不要让类派生至具体类
- 不要覆盖基类中实现的方法
类图及代码:
1、简单工厂
1 public class SimplePizzaFactory { 2 public Pizza createPizza(String type) { 3 Pizza pizza = null; 4 5 if (type.equals("cheese")) { 6 pizza = new CheesePizza(); 7 } else if (type.equals("pepperoni")) { 8 pizza = new PepperoniPizza(); 9 } else if (type.equals("clam")) { 10 pizza = new ClamPizza(); 11 } else if (type.equals("veggie")) { 12 pizza = new VeggiePizza(); 13 } 14 return pizza; 15 } 16 }
2、工厂模式
1 public abstract class PizzaStore { 2 3 //这里定义一个工厂方法 4 abstract Pizza createPizza(String item); 5 6 public Pizza orderPizza(String type) { 7 8 Pizza pizza = createPizza(type); 9 10 System.out.println("--- Making a " + pizza.getName() + " ---"); 11 pizza.prepare(); 12 pizza.bake(); 13 pizza.cut(); 14 pizza.box(); 15 16 return pizza; 17 } 18 }
1 public class ChicagoPizzaStore extends PizzaStore { 2 3 Pizza createPizza(String item) { 4 if (item.equals("cheese")) { 5 return new ChicagoStyleCheesePizza(); 6 } else if (item.equals("veggie")) { 7 return new ChicagoStyleVeggiePizza(); 8 } else if (item.equals("clam")) { 9 return new ChicagoStyleClamPizza(); 10 } else if (item.equals("pepperoni")) { 11 return new ChicagoStylePepperoniPizza(); 12 } else return null; 13 } 14 }
1 public class PizzaTestDrive { 2 3 public static void main(String[] args) { 4 PizzaStore nyStore = new NYPizzaStore(); 5 6 Pizza pizza = nyStore.orderPizza("cheese"); 7 System.out.println("Ethan ordered a " + pizza.getName() + "\\n"); 8 9 pizza = nyStore.orderPizza("clam"); 10 System.out.println("Ethan ordered a " + pizza.getName() + "\\n"); 11 } 12 }
3、抽象工厂
先来定义一个接口PizzaIngredientFactory,他定义了一系列的创建Pizza材料的方法
1 public interface PizzaIngredientFactory { 2 3 public Dough createDough(); 4 public Sauce createSauce(); 5 public Cheese createCheese(); 6 public Veggies[] createVeggies(); 7 public Pepperoni createPepperoni(); 8 public Clams createClam(); 9 10 }
子类
1 public class NYPizzaIngredientFactory implements PizzaIngredientFactory { 2 3 public Dough createDough() { 4 return new ThinCrustDough(); 5 } 6 7 public Sauce createSauce() { 8 return new MarinaraSauce(); 9 } 10 11 public Cheese createCheese() { 12 return new ReggianoCheese(); 13 } 14 15 public Veggies[] createVeggies() { 16 Veggies veggies[] = { new Garlic(), new Onion(), new Mushroom(), new RedPepper() }; 17 return veggies; 18 } 19 20 public Pepperoni createPepperoni() { 21 return new SlicedPepperoni(); 22 } 23 24 public Clams createClam() { 25 return new FreshClams(); 26 } 27 }
Pizza类
1 public class CheesePizza extends Pizza { 2 //这里组合了一个PizzaIngredientFactory对象的引用,用于提供不同的原料 3 PizzaIngredientFactory ingredientFactory; 4 5 /** 6 * 通过传入一个PizzaIngredientFactory原料工厂,我们可以在制作Pizza的时候动态的产生所需要的原料 7 * @param ingredientFactory 8 */ 9 10 public CheesePizza(PizzaIngredientFactory ingredientFactory) { 11 this.ingredientFactory = ingredientFactory; 12 } 13 14 void prepare() { 15 System.out.println("Preparing " + name); 16 dough = ingredientFactory.createDough(); 17 sauce = ingredientFactory.createSauce(); 18 cheese = ingredientFactory.createCheese(); 19 } 20 }
Pizza商店
1 public class NYPizzaStore extends PizzaStore { 2 3 protected Pizza createPizza(String item) { 4 Pizza pizza = null; 5 PizzaIngredientFactory ingredientFactory = new NYPizzaIngredientFactory(); 6 7 if (item.equals("cheese")) { 8 9 pizza = new CheesePizza(ingredientFactory); 10 pizza.setName("New York Style Cheese Pizza"); 11 12 } else if (item.equals("veggie")) { 13 14 pizza = new VeggiePizza(ingredientFactory); 15 pizza.setName("New York Style Veggie Pizza"); 16 17 } else if (item.equals("clam")) { 18 19 pizza = new ClamPizza(ingredientFactory); 20 pizza.setName("New York Style Clam Pizza"); 21 22 } else if (item.equals("pepperoni")) { 23 24 pizza = new PepperoniPizza(ingredientFactory); 25 pizza.setName("New York Style Pepperoni Pizza"); 26 27 } 28 return pizza; 29 } 30 }
以上是关于工厂模式&抽象工厂——HeadFirst设计模式学习笔记的主要内容,如果未能解决你的问题,请参考以下文章