`
webcode
  • 浏览: 6129373 次
  • 性别: Icon_minigender_1
  • 来自: 上海
文章分类
社区版块
存档分类
最新评论

工厂模式

 
阅读更多

案例场景:有一家汽车工厂,他们生产各类汽车,有小汽车、公交车、摩托车,举例就这三种吧,当生产商需要购买汽车的时候,直接从汽车工厂里面取,具体那些汽车是怎样制造出来的,厂商不用去管,他只需要看到要购买的汽车以及汽车质量有保证即可。在这个场景中用到了我们的简单工厂模式。

在OO设计领域,我们知道前人总结了不少的经验,许多的经验在现代软件工程过程中已经被认为是原则来遵守。下面笔者摘抄几项下文涉及到的OO原则的定义。
OCP(开闭原则,Open-Closed Principle):一个软件的实体应当对扩展开放,对修改关闭。我的理解是,对于一个已有的软件,如果需要扩展,应当在不需修改已有代码的基础上进行。
DIP(依赖倒转原则,Dependence Inversion Principle):要针对接口编程,不要针对实现编程。我的理解是,对于不同层次的编程,高层次暴露给低层次的应当只是接口,而不是它的具体类。

在以前,我们会发现一个现象:比如下面的代码

package cn.com.factor;

//定义一个车的接口
public interface Vehicle {
	public void create();
}

//小轿车的实现类
class Car implements Vehicle{
	@Override
	public void create() {
		System.out.println("生产了一辆小轿车");
	}
}

class Test{
	public static void main(String[] args) {
		Vehicle car=new Car();
		car.create();
	}
}

我们会发现不满足DIP开闭原则,因为客户端在调用的时候,把接口的实现类Car给暴露给了客户端,那么,我们应该怎样解决呢,使用简单工厂方法即可解决。

简单工厂模式:是类的创建模式,又叫做静态工厂方法模式,是由一个工厂对象决定出哪一种产品类的实例,通常它根据自变量的不同返回不同类的实例。

简单工厂方法的实质是由一个工厂类根据传入的参数,动态决定应该创建出哪一个产品类的实例。

简单工厂模式的构成

工厂类角色(Creator):担任这个角色的是简单工厂模式的核心,含有与应用紧密相关的商业逻辑。工厂类在客户端的直接调用下创建产品对象,它往往由一个具体类实现。

抽象产品(Abstract Product)角色担任这个角色的类是工厂方法模式所创建的对象的父类,或它们共同拥有的接口。通常使用Java 接口或者抽象Java 类实现这一角色。

具体产品(Concrete Product)角色抽象工厂模式所创建的任何产品对象都是某一个具体产品类的实例。这是客户端最终需要的东西,其内部一定充满了应用系统的商业逻辑。通常使用具体Java 类实现这个角色。

代码场景模拟:

package cn.com.factor;
//抽象产品角色:定义一个车的接口
public interface Vehicle {
	public void create();
}

package cn.com.factor;
//具体产品角色:小轿车的实现类
public class Car implements Vehicle {
	@Override
	public void create() {
		System.out.println("生产了一辆小轿车");
	}
}

package cn.com.factor;
//具体产品角色:公交车的实现类
public class Bus implements Vehicle {
	@Override
	public void create() {
		System.out.println("生产了一辆公交车");
	}
}

package cn.com.factor;
//具体产品角色:摩托车的实现类
public class MotorCar implements Vehicle {
	@Override
	public void create() {
		System.out.println("生产了一辆摩托车");
	}
}
package cn.com.factor;
//工厂类角色
public class Factory {
	public static Vehicle getVehicle(String str){
		if("小轿车".equals(str)){
			return new Car();
		}
		if("公交车".equals(str)){
			return new Bus();
		}
		if("摩托车".equals(str)){
			return new MotorCar();
		}
		return null;
	}
}

package cn.com.factor;
//测试类
public class Test {
	public static void main(String[] args) {
		//厂家要一辆小轿车
		Vehicle car=Factory.getVehicle("小轿车");
		car.create();
		//厂家要一辆公交车
		Vehicle bus=Factory.getVehicle("公交车");
		bus.create();
		//厂家要一辆摩托车
		Vehicle motor=Factory.getVehicle("摩托车");
		motor.create();
		
	}
}

这样,客户端只要相应的车就可以了,他不可能知道车子是怎样制造出来的,也就是说不知道具体的实现类,工厂只提供了车的一个接口。

我们用OCP看看简单工厂,会发现如果要对系统进行扩展的话治需要增加实现产品接口的产品类(上例表现为“小轿车”,“公交车”类,比如要增加个“电动车”类),而无需对原有的产品类进行修改。这咋一看好像满足OCP,但是实际上还是需要修改代码的——对,就是修改工厂类。上例中如果增加“电动车”产品类,就必须相应的修改“Factory”工厂类,增加个判断。所以可以看出,简单工厂模式是不满足OCP的。这时,我们可以使用抽象工厂模式:

工厂方法模式是对象的创建模式,它是工厂方法模式的进一步推广。假设一个子系统需要一些产品对象,而这些产品又属于一个以上的产品等级结构。那么为了将消费 这些产品对象的责任和创建这些产品对象的责任分割开来,可以引进抽象工厂模式。这样的话,消费产品的一方不需要直接参与产品的创建工作,而只需要向一个公 用的工厂接口请求所需要的产品。

修改工厂方法模式中的角色

抽象工厂(AbstractFactory)角色:担任这个角色的是工厂方法模式的核心,它是与应用系统的商业逻辑无关的。通常使用Java 接口或者抽象Java 类实现,而所有的具体工厂类必须实现这个Java 接口或继承这个抽象Java 类。

具体工厂类(Conrete Factory)角色:这个角色直接在客户端的调用下创建产品的实例。这个角色含有选择合适的产品对象的逻辑,而这个逻辑是与应用系统的商业逻辑紧密相关的。通常使用具体Java 类实现这个角色。

修改实例代码:

比如说现在工厂改革了,他又分为小工厂,有专门制造小轿车、专门制造摩托车...

package cn.com.factor;
//增加抽象工厂角色
public interface IFactory {
	public Vehicle getVehicle();
}

package cn.com.factor;
//制造小轿车的工厂
public class CarFactory implements IFactory{
	@Override
	public Vehicle getVehicle() {
		return new Car();
	}
}
package cn.com.factor;
//制造摩托车的工厂
public class MotorFactory implements IFactory {
	@Override
	public Vehicle getVehicle() {
		return new MotorCar();
	}
}
测试:

//让制造小轿车的工厂生产小轿车
IFactory car1=new CarFaactory();
car1.getVehicle();
//让制造摩托车的工厂生产摩托车
IFactory motor1=new MotorFactory();
motor1.getVehicle();

这样,我们便容易拓展和维护我们的代码。

抽象工厂模式

当我们制造车的厂又想制造电脑了,生产各种品牌的电脑,我们就会这样来定义:

//增加抽象工厂角色
public interface IFactory {
 public Vehicle getVehicle();
 public Computer getComputer();//电脑
}
然后写如电脑的一个抽象类以及实现类,这样针对与产品的抽象我们定义为抽象工厂模式,
它对工厂的抽象程度更高。
深入理解:

一:工厂方法模式的核心是一个抽象工厂类,而简单工厂模式把核心放到了一个具体类上.简单工厂是工厂方法模式的特例。
工厂方法模式和抽象工厂模式的最主要的区别在于对工厂的抽象程度上。
抽象工厂模式中一般是抽象出工厂接口,表示他就是一个工厂,而不管它是制造什么产品的工厂,他的抽象程度较高。
而工厂厂
方法模式的抽象工一般是针对于产品进行抽象。表示它是一个生产某类产品的工厂简单工厂是不支持继承的,如果需要建立的对象过多,会使这个类变大,建立偶合性集中在这个类上.
工厂方法解决了简单工厂不支持继承的缺点.
以上两个模式所建立的对象是在一个等级结构中.
抽象工厂是面向多个平行等级结构的,其建立对象的原则是以簇(功能相似的对象)为单位划分需要建立的对象.

二:工厂方法创建一般只有一个方法,创建一种产品。
抽象工厂一般有多个方法,创建一系列产品。 目的不一样工厂方法创建 "一种" 产品,他的着重点在于"怎么创建",也就是说如果你开发,你的大量代码很可能围绕着这种产品的构造,初始化这些细节上面。也因为如此,类似的产品之间有很多可以复用的特征,所以会和模版方法相随。 抽象工厂需要创建一些列产品,着重点在于"创建哪些"产品上,也就是说,如果你开发,你的主要任务是划分不同差异的产品线,并且尽量保持每条产品线接口一致,从而可以从同一个抽象工厂继承。



简单工厂模式与工厂方法模式区别
从以上对两种模式的介绍可以了解到,工厂方法模式是为了克服简单工厂模式的缺点(主要是为了满足OCP)而设计出来的。但是,工厂方法模式就一定比简单工厂模式好呢?笔者的答案是不一定。下面笔者将详细比较两种模式。

1. 结构复杂度
从这个角度比较,显然简单工厂模式要占优。简单工厂模式只需一个工厂类,而工厂方法模式的工厂类随着产品类个数增加而增加,这无疑会使类的个数越来越多,从而增加了结构的复杂程度。

2.代码复杂度
代码复杂度和结构复杂度是一对矛盾,既然简单工厂模式在结构方面相对简洁,那么它在代码方面肯定是比工厂方法模式复杂的了。简单工厂模式的工厂类随着产品类的增加需要增加很多方法(或代码),而工厂方法模式每个具体工厂类只完成单一任务,代码简洁。

3.客户端编程难度
工厂方法模式虽然在工厂类结构中引入了接口从而满足了OCP,但是在客户端编码中需要对工厂类进行实例化。而简单工厂模式的工厂类是个静态类,在客户端无需实例化,这无疑是个吸引人的优点。

4.管理上的难度
这是个关键的问题。
我们先谈扩展。众所周知,工厂方法模式完全满足OCP,即它有非常良好的扩展性。那是否就说明了简单工厂模式就没有扩展性呢?答案是否定的。简单工厂模式同样具备良好的扩展性——扩展的时候仅需要修改少量的代码(修改工厂类的代码)就可以满足扩展性的要求了。尽管这没有完全满足OCP,但笔者认为不需要太拘泥于设计理论,要知道,sun提供的java官方工具包中也有想到多没有满足OCP的例子啊(java.util.Calendar这个抽象类就不满足OCP,具体原因大家可以分析下)。
然后我们从维护性的角度分析下。假如某个具体产品类需要进行一定的修改,很可能需要修改对应的工厂类。当同时需要修改多个产品类的时候,对工厂类的修改会变得相当麻烦(对号入座已经是个问题了)。反而简单工厂没有这些麻烦,当多个产品类需要修改是,简单工厂模式仍然仅仅需要修改唯一的工厂类(无论怎样都能改到满足要求吧?大不了把这个类重写)。

由以上的分析,笔者认为简单工厂模式更好用更方便些。当然这只是笔者的个人看法而已,毕竟公认的,工厂方法模式比简单工厂模式更“先进”。但有时过于先进的东西未必适合自己,这个见仁见智吧。

分享到:
评论
1 楼 kevenfox 2014-01-15  
生产电脑不应该修改原来的接口,修改的成本太大,这同样不符合开闭原则。

相关推荐

    qt工厂模式例子qt简单工程模式源码

    3. Qt工厂模式工程 4. Qt工厂模式例程 5. Qt工厂模式例子 6. 简单工厂模式 部分源码实例: // 奔驰工厂 class BenzFactory : public AFactory { public: ICar* CreateCar() { return new BenzCar(); } }; // ...

    导航进入工厂模式的方法

    工厂模式,也称为工程模式或调试模式,是制造商为了测试和调整设备功能而设置的一种特殊模式。在这个模式下,用户可以访问和修改通常隐藏的高级设置,包括地图数据、系统参数以及硬件诊断。下面我们将详细介绍如何...

    工厂模式:简单工厂模式、工厂方法模式、抽象工厂模式

    工厂模式是一种常用的软件设计模式,它是创建型设计模式的一种,主要解决对象的创建问题,将对象的创建过程封装起来,使得创建过程独立于使用过程。这样可以提高代码的可复用性和灵活性,同时降低了系统的耦合度。...

    JAVA设计模式(01):创建型-工厂模式【简单工厂模式】(Simple Factory)

    **简单工厂模式**是软件设计模式中的一种,属于创建型模式。在Java编程中,它是一种用于创建对象的简便方法,将对象的实例化过程封装到一个单独的工厂类中,使得客户端代码无需直接调用具体类的构造函数,而是通过...

    各机芯进入工厂模式汇总

    - 关机状态下,同时按住“音量-”和“电源”键,屏幕亮起后松开,一般会进入工程模式,从中可以选择工厂模式。 4. MediaTek(联发科)机芯: - 长按遥控器的“设置”和“返回”键,开机后会进入工程模式,选择相应...

    酷派各种机型进工程模式方法

    其中,"工程模式"是一个特殊的功能,通常隐藏在系统深处,主要用于制造商进行硬件测试和调试。对于用户而言,进入工程模式可以获取更多关于手机硬件的信息,进行高级设置,甚至解决一些特定问题。本篇文章将详细介绍...

    简单工厂模式-工厂方法模式-抽象工厂模式

    在软件设计模式中,工厂模式是一组非常基础且实用的设计模式,主要分为简单工厂模式、工厂方法模式和抽象工厂模式。这些模式都是为了解决对象创建的问题,通过封装对象的创建过程,使得代码更加灵活,易于扩展和维护...

    AOC电视进入酒店模式和工厂模式的方法

    测试机型:32m3095(其它机型未试,大同小异,自行测试) 测试时间:2022.06.15 进入酒店模式好处:可以设置...进入工厂模式好处:可以设置不正常的颜色,声音。恢复系统默认设置。好多功能,是英文的,我看不懂。

    进入Moto Z1工程模式的方法

    【进入Moto Z1工程模式的方法】 Moto Z1是一款由摩托罗拉公司推出的CDMA机型,其工程模式是为专业技术人员和高级用户设计的特殊功能区,可以用来进行设备诊断、硬件测试以及一些系统级别的调整。以下是两种进入Moto...

    乐华板卡 进工程模式方法

    根据提供的文档内容,本文将详细解释乐华板卡如何进入工程模式的方法,主要涉及Novatek和Realtek两种方案下的具体操作步骤。 ### 一、Novatek方案进特殊模式方法 #### 1. 板卡型号:PT系列 **1.1 工厂菜单** - *...

    进入凯立德 工程模式 的方法

    进入凯立德 工程模式 的方法 在“查找”菜单中切换到“123”输入法,输入*147#即可进入工程模式

    设计模式单例模式和工厂模式综合应用

    "设计模式单例模式和工厂模式综合应用"的主题聚焦于两种常用的设计模式:单例模式和工厂模式,并探讨它们如何协同工作来实现高效、灵活的代码结构。这个主题尤其适用于Java编程语言,因为Java的面向对象特性使得设计...

    简单工厂模式、工厂模式、抽象工厂模式案例(C++实现)

    在软件工程中,设计模式是解决常见问题的模板或最佳实践。工厂模式是其中最常用的一种,它提供了创建对象的最佳方式。在这个压缩包中,包含了三种工厂模式的C++实现:简单工厂模式、工厂方法模式以及抽象工厂模式。...

    JAVA 设计模式 工厂模式 代理模式 迭代模式 责任链模式 源码

    以下是关于JAVA设计模式中提及的四种模式——工厂模式、代理模式、迭代器模式以及责任链模式的详细说明。 1. **工厂模式**:工厂模式是一种创建型设计模式,它提供了一种创建对象的最佳方式。在工厂模式中,当创建...

    C++设计模式-工程模式

    "C++设计模式-工程模式"这个标题暗示我们将深入探讨C++中的一种核心设计模式——工厂模式。工厂模式是创建型设计模式,它提供了一种创建对象的最佳方式,允许我们在不指定具体类的情况下创建对象。在描述中提到的...

    抽象工厂模式+工厂方法模式+策略模式+类图实现手机加工厂

    本文将探讨三个重要的设计模式:抽象工厂模式、工厂方法模式以及策略模式,并结合一个实际的场景——手机加工厂,来具体阐述它们的应用。 首先,我们来看**抽象工厂模式**。这个模式主要用于创建相关或依赖对象的...

    工厂模式源代码

    《工厂模式源代码》 工厂模式是软件设计模式中的一种,属于创建型模式,它提供了一种创建对象的最佳方式。在工厂模式中,当我们创建对象时,不会直接实例化具体的产品类,而是通过一个共同的接口或者抽象类,即工厂...

    工厂方法模式和抽象工厂模式的区别

    工厂方法模式和抽象工厂模式是两种常见的设计模式,它们都属于创建型模式,用于解决对象的创建问题。在软件设计中,这两种模式都是用来隔离对象的创建和使用,以提高系统的灵活性和可扩展性。 首先,工厂方法模式的...

    工厂模式(简单工厂,普通工厂,抽象工厂)代码java

    在软件设计模式中,工厂模式是一种非常常用的行为型模式,它的主要目的是为了隔离对象的创建过程,使得客户端代码不直接创建对象,而是通过一个工厂类来负责对象的创建。这样可以使得系统更具可扩展性和可维护性。...

    工厂模式(2016手机案例)

    工厂模式是一种设计模式,它是创建型模式的一种,主要用于在代码中抽象出对象的创建过程,使得创建对象的过程与具体的实现分离,从而提高了代码的可扩展性和可维护性。在这个"工厂模式(2016手机案例)"中,我们将...

Global site tag (gtag.js) - Google Analytics