工厂模式,故名思义,就是你要某种东西的工厂,它负责为你生产产品,你只要拿来使用便可,无需关心如何生成。 编程
除了使用new操做符外,还有不少制造对象的方法。好比说工厂模式。在实际的应用中,咱们大量地初始化会形成“耦合”问题。那该怎么办? 设计模式
当遇到"new",就会想到"具体".什么意思呢?当使用new对一个类进行实例化时,咱们使用的是实现,但不是接口。这样一来,会致使代码失去良好的弹性。由于彼此之间已经被你绑定到一块儿了。例如: this
Person p = new Person();当有一群相关的具体类时,就会看到这样的代码: spa
if(speaking){ 设计
Person p = new Person;} 对象
else if(singing) { Person p = new Person();} 接口
else if(dancing){ Person p = new Person(); } 内存
在上述代码中,有一些要实例化的具体类,究竟要实例化哪一个,要在运行时由一些逻辑条件来决定。 ci
这样的代码,若需求再也不有新的变化还能够,可是,若一旦有变化,就必须从新打开这段代码进行检查和修改。毫无疑问,这样的代码会形成部分系统更难维护和更新,并且也更容易犯错。 产品
为何?
仅从技术上来讲,new没错,就是为咱们在内存中申请一份空间,而后存储临时数据。若是在头效率与可维护性性的角度上来讲,就有些差强人意了。进而,便有大师们提出了 面向接口编程。一切都应当参照抽象,而不是具体实现。面向接口编程,能够隔离掉之后系统可能发生的大量变化。由于,面向接口编程,经过多态能够与任何新类实现该接口。接口,也相应地体现了OO原则:对扩展开放,对修改封闭。
下面内容引自 《HeadFirst 设计模式》:
识别变化的方面 假设你有一个比萨店,代码实现以下:
Pizza orderPizza(){
Pizza pizza = new Pizza();
pizza.prepare(); // 作比萨前的准备
pizza.bake(); // 烧烤
pizza.cut(); // 切饼
pizza.box(); // 包装
return pizza;
}
可是,当你须要更多比萨类型时,怎么解决?因此,必须增长一些代码,来"决定"适合的比萨类型,而后再"制造"这个比萨:
Pizza orderPizza(String type){ // type参数----比萨类型
Pizza pizza;
if(type.equals("cheese")){ pizza = new CheesePizza();}
else if(type.equals("greek")){ pizza = new GreekPizza();}
else if(type.equals("pepperoni")){ pizza = new PepperoniPizza();}
pizza.prepare(); // 作比萨前的准备
pizza.bake(); // 烧烤
pizza.cut(); // 切饼
pizza.box(); // 包装
return pizza;
}
可是,若是要增长更多地比萨类型,咱们上面的这些代码就又得从新写过,并且有至关一部分是重复的。因此,此时应该考虑 封装。
首先,把建立对象的代码从orderPizza()方法中抽离出去,而后把这些代码放在一个对象中,这个新对象只管如何建立比萨,若是任何对象想要建立比萨,直接找它就对了。
Pizza orderPizaa(String type){
pizza.prepare(); // 作比萨前的准备
pizza.bake(); // 烧烤
pizza.cut(); // 切饼
pizza.box(); // 包装
}
这样一来,就有了 工厂 SimplePizzaFactory; 当须要比萨时,就叫SimplePizzaFactory生产一个。如今,orderPizza()方法只关心从工厂获得了一个比萨,而这个比萨实现了Pizza接口,因此能够调用 prepare(),bake(),cut(),box()来分别进行准备、烘烤、切片、装盒
public class SimplePizzaFactory{
public Pizza createPizza(String type){
Pizza pizza = null;
if(type.equals("cheese")){ pizza = new CheesePizza();}
else if(type.equals("greek")){ pizza = new GreekPizza();}
else if(type.equals("pepperoni")){ pizza = new PepperoniPizza();}
return pizza;
}
public class PizzaStore{
SimplePizzaFactory factory;
public PizzaStore(SimplePizzaFactory facatory){ this.factory = factory; }
public Pizza orderPizza(String type)
{ Pizza pizza ;
pizza = factory.createPizza(type); // 比萨工厂根据传入的参数来生产相应的比萨
pizza.prepare();
pizza.bake();
pizza.cut(); pizza.box();
}
}
}
在上面的修改后,代码之间已经不是很大程度地耦合了。并且,实现与扩展也较好地分离,从而提升了代码的弹性。
待续...