设计模式----工厂模式
一 简单工厂模式
1.简单工厂模式:属于类的创建型模式,又叫静态工程模式,通过一个专门的类来负责创建其他类的实例,被构建的类往往都有一个公共的父类或者父接口。
2.代码实现略
3.从1的uml图中可以分析出简单工厂模式的优缺点
优点:
1)首先将产品的创建的逻辑放到了工厂中,从而避免了客户端与具体的实现类直接的耦合,只是根据实现类的类型或者名称来获取实例。满足里式替换原则。
2)隔离了客户端没有必要去了解具体产品的实现的细节。
缺点:
1)因为在工厂类中封装了创建那种类的判断逻辑 违背了单一职责的原则。如果增加其他产品的品种不得不修改工厂中的判断的逻辑也就是要重新编译改工厂类丧失了灵活性和可维护性。
2)一般静态工厂,都是静态的方法。因此无法发挥面向对象三大特性中,多态的动态分派。无法形成基于继承的继承树的结构。
4.实际应用
以java中的jdbc来举例说明,先看一下uml图:
JDBC是SUN公司提供的一套数据库编程接口API,它利用Java语言提供简单、一致的方式来访问各种关系型数据库。Java程序通过JDBC可以执行SQL语句,对获取的数据进行处理,并将变化了的数据存回数据库,因此,JDBC是Java应用程序与各种关系数据进行对话的一种机制。用JDBC进行数据库访问时,要使用数据库厂商提供的驱动程序接口与数据库管理系统进行数据交互。
客户端要使用使用数据时,只需要和工厂进行交互即可,这就导致操作步骤得到极大的简化,操作步骤按照顺序依次为:注册并加载数据库驱动,一般使用Class.forName();创建与数据库的链接Connection对象;创建SQL语句对象preparedStatement(sql);提交SQL语句,根据实际情况使用executeQuery()或者executeUpdate();显示相应的结果;关闭数据库。
注:即客户端调用的时候,就没有必要跟具体的数据库耦合在一块了
二、工厂方法模式
UML类图如下:
这个和简单工厂有区别,简单工厂模式只有一个工厂,工厂方法模式对每一个产品都有相应的工厂
好处:增加一个运算类(例如N次方类),只需要增加运算类和相对应的工厂,两个类,不需要修改工厂类。
缺点:增加运算类,会修改客户端代码,工厂方法只是把简单工厂的内部逻辑判断移到了客户端进行。
三 抽象工厂模式:参考大话设计模式
UML类图如下:
从图上可以看出这和工厂方法模式很相似,但是呢,有几个区别:
抽象工厂模式,一个具体工厂可以制造几个产品,例如微软工厂(相当于SqlserverFactory)可以制造微软鼠标(属于鼠标类,鼠标类下面有惠普鼠标,微软鼠标等,相当于上图中的IDepartment下面的SqlserverDepartment和AccessDepartment),也可以制造微软键盘(属于键盘类,键盘类下面有惠普键盘,微软键盘等,相当于上图中的IUser下面的SqlserverUser和AccessUser)。
参考网上http://blog.csdn.net/wangwenhui11/article/details/3955125中的话:
工厂方法模式:一个抽象产品类,可以派生出多个具体产品类。
一个抽象工厂类,可以派生出多个具体工厂类。
每个具体工厂类只能创建一个具体产品类的实例。
抽象工厂模式:多个抽象产品类,每个抽象产品类可以派生出多个具体产品类。
一个抽象工厂类,可以派生出多个具体工厂类。
每个具体工厂类可以创建多个具体产品类的实例。
区别:工厂方法模式只有一个抽象产品类,而抽象工厂模式有多个。
工厂方法模式的具体工厂类只能创建一个具体产品类的实例,而抽象工厂模式可以创建多个。
抽像工厂优缺:
优点:易于交换产品系列,例如Access和SQLServer数据库之间切换。
缺点:例如增加一个机箱产品,不仅需要添加三个类“机箱类,微软机箱,惠普机箱”,还要修改惠普工厂,微软工厂支持制造机箱。而添加一个联想工厂的时候,只需要添加三个类,使用联想工厂还是要修改客户端代码的。
在《大话设计模式》中,提出用简单工厂模式改进抽象工厂模式的方法。
DataAccess的代码如下:
这样,在DataAccess里面直接指定数据库(指定品牌),当需要换数据库(or 品牌)的时候,修改DataAccess内的代码。
当然可以用反射方法修改数据库,这样,只需要修改配置文件。就完美的改善了抽象工厂的缺点,而且在客户端不用修改代码。
反射实现:
要修改db属性:
这里面用的就是利用反射来去除了switch或if解除分支带来的耦合。