工厂模式根据抽象程度可分为三种,分别为:简单工厂模式,工厂方法模式和抽象工厂模式。他的主要优点有:
1、使代码结构清晰,有效的额封装变化。在编程中,产品类的实例化有时候是比较复杂和多变的,通过工厂模式,将产品的实例化封装起来,使得调用者根本无需关心产品实例化过程,只需依赖工厂即可得到自己想要的产品。
2.对调用者屏蔽具体的产品类。如使用工厂模式,调用者只需关心产品的接口就你可以了,至于具体实现,调用者根本无需关心。即使变更了具体的实现,对调用者来说没有任何影响。
3.降低耦合度。产品类的实例化通常来说是很复杂的,他需要依赖很多的类,而这些类对于调用者来说根本无需知道,如果使用了工厂方法,我们需要做的仅仅是实例化好产品类,然后交给调用者使用。对调用者来说,产品所依赖的类都是透明的。
三种工厂模式具有类似的特性,使用场景也类似。首先作为一种创建类模式,在任何需要生成复杂对象的地方,都可以使用工厂模式(简单对象只要通过new就可以完成创建对象),其次,工厂模式是一种典型的解耦模式,迪米特法则在工厂模式中体现的尤为明显。假如调用者自己组装产品需要增加依赖关系时,可以考虑采用工厂模式。将会 大大降低对象之间的耦合度。再次,由于工厂模式是依靠抽象架构的,他把实例化产品的任务交给实现类完成,扩展性比较好。也就是说当需要系统有比较好的扩展性的时候,可以考虑采用工厂模式,不用的产品用不同的实现工厂来组装。
下面就对三个工厂模式分别介绍。
一、简单工厂模式
简单工厂模式时类的创建模式,又叫静态工厂方法模式。简单工厂模式就是由一个工厂类根据传入的参数决定创建哪一种的产品类。
共有4个角色:
1.工厂类角色:是具体产品类角色直接调用者
2.抽象产品角色:接口或者抽象类,具体负责产品角色的定义,及与客户端的交互
3.具体产品角色:被工厂类创建的对象,也是客户实际操作的对象。
4.客户端:调用工厂类生产实例,并调用实例的方法进行相应的工作。
举个例子:
public interface people{ //工厂类角色
public void say();
}
public class chinese implements people{ //具体产品角色1
public void say(){
System.out.println("说中国话");
}
}
public class american implements people{ //具体产品角色2
public void say(){
System.out.println("speak english");
}
}
public class peopleFactory{ //抽象产品角色
public static people create(int type){
if(type==1){
return new chinese();
}else if(type==2){
return new american();
}
}
}
public class test{ //客户端
public static void main(String []args){
people p=peopleFactory.create(1);
p.say();
p=peopleFactory.create(2);
p.say();
}
}
简单工厂模式优点有:客户端不需要修改代码
缺点有:当需要增加新的具体产品类的时候,不仅需要新增加具体产品类,还要修改工厂类,违反了开闭原则。
二、工厂方法模式
工厂方法模式时简单工厂模式的衍生,解决了许多简单工厂模式的问题。首先工厂方法模式完全实现了“开放-封闭原则”,实现了可扩展性。其次更复杂的层次结构,可以应用于产品结果复杂的场合。
工厂模式方法的对简单工厂模式进行了抽象。有一个抽象的Factory类(可以是抽象类和接口),这个类将不再负责具体的产品生产,而是只制定一些规范,具体的生产工作由其子类去完成。在这个模式中,工厂类和产品类依次对应。即一个抽象工厂对应一个抽象产品,一个工厂对应一个具体产品,这个具体的工厂就负责生产对应的产品。
工厂方法模式是最典型的模板方法模式应用。
举个栗子:
public interface Icar{
public void docar();
}
public class bwm implements Icar{
public void docar(){
System.out.println("我是宝马,别摸我");
}
}
public class buick implements Icar{
public void docar(){
System.out.println("我是别克,很酷");
}
}
public interface Icarfactory{
public Icar createCar();
}
public class bmwFactory implements Icarfactory{
public Icar createCar(){
return new bwm();
}
}
public class buickFactory implements Icarfactory{
public Icar createCar(){
return new buick();
}
}
public class test{
public static void main(String []args){
Icarfactory factory=new bmwFactory();
Icar bwm= factory.createCar();
bwm.docar();
factory=new buickFactory();
Icar buick= factory.createCar();
buick.docar();
}
}
基于面向接口编程的原理,创建部分成为抽象工厂和实体工厂。创建出的对象成为抽象产品和实体产品。多了一个对象,只需添加一套对应的工厂和产品就可以了,不需要修改源代码。
工厂方法模式和简单工厂模式的区别是:简单工厂模式只有一个工厂,工厂方法模式对每一个 产品都有相应的工厂。好处是:增加一个运算类和相对应的工厂,两个类,不需要修改工厂类。缺点是:增加运算类,会修改客户端代码,工厂方法模式只是把简单工厂模式的内部逻辑判断移到了客户端进行。
三、抽象工厂模式
抽象工厂模式是围绕一个超级工厂创建其他工厂。该超级工厂又称为其他工厂的工厂。这种类型的设计模式属于创建型模式。它提供了创建对象的最佳方式。
在抽象工厂模式中,接口是负责创建一个相关对象的工厂,不需要显示指定他们的类。每个生成的工厂都能按照工厂模式提供对象。
抽象工厂模式和工厂方法模式的区别:工厂方法模式只有一个抽象产品类,而抽象工厂模式有多个。工厂方法模式的具体工厂类只能创建一个具体产品类的实例,而抽象工厂模式可以创建多个 。每个模式都是针对一定问题的解决方案,工厂方法模式针对的是产品等级结构,而抽象方法模式针对的是多个产品等级结果。
抽象工厂模式的优缺点:优点:易于交换产品系列。
缺点:例如增加一个机箱产品,不仅需要添加多个类还要修改客户端代码。