设计模式(1) - Factory工厂模式
来源:互联网 发布:淘宝达人怎么直播 编辑:程序博客网 时间:2024/05/22 14:04
Factory(工厂)模式大致可以分为三种:简单工厂模式,工厂方法模式以及抽象工厂模式。
ConcreteProductA
ConcreteProductB
工厂方法模式,也存在一定的缺陷:
1).只要每增加一种新的产品,就需要相应的增加一个工厂,这样会产生大量的类。比起简单工厂模式,这种模式需要更多的类。这样,Factory的接口永远就无法封闭了。
(当然,也有其它方法可以解决此问题。可以通过给Factory Method传递一个类型参数,来决定具体要创建哪种Product;或者利用模板,将具体的Product类做为模板参数).
2).Factory模式存在局限性。它仅仅局限于一种类,即具体的产品类都有一个共同基类Product。如果需要为不同类型的类提供一个对象创建的接口,此方法就不行了。
举例说明:电脑做为一种产品,即有笔记本电脑(Laptop),也有台式机(Computer)。其中,每种产品又有不同的生产/实现者。因此,有下面的实现:
ProductLenovoLaptop
ProductLenovoComputer
ProductDellLaptop
ProductDellComputer
从上面看出,当需要创建一组对象(ProductLenovoLaptop, ProductLenovoComputer)的时候,只需要维护一个创建对象(ConcreteFactoryLenovo)即可。
事实上,AbstractFactory模式是为创建一组相关或依赖的对象提供创建接口,而Factory是为一类对象提供创建接口或延迟对象的创建到子类中实现。并且,可以看出AbstractFactory模式通常都是使用Factory模式实现的(ConcreteFactoryA)。
基于上面的例子:同样是Laptop和Computer,它们都可以由厂家生产,但是有不同的实现。有Lenovo和Dell两家生产出来的不同的Laptop与Computer。而负责生产Laptop与Computer就是Factory模式了。
1. 简单工厂模式
首先是简单工厂模式。主要逻辑是在工厂类中进行判断,根据类型生产出对应的产品。当需要增加新的产品时,就需要修改工厂类。换言之,抽象出一个公共接口形成抽象类或者接口,然后声明一个指向基类的指针,来指向实际的子类,以达到多态目的。#include<iostream>using namespace std;enum PRODUCTTYPE {TYPEA, TYPEB};class Product{public:virtual ~Product(){};virtual void show() = 0;};class ConcreteProductA:public Product{public:void show(){ cout<<"ConcreteProductA"<<endl; }};class ConcreteProductB:public Product{public:void show() { cout<<"ConcreteProductB"<<endl;}};class SimpleFactory{public:Product *CreateProduct(enum PRODUCTTYPE type){if(TYPEA == type) return new ConcreteProductA();else if(TYPEB == type)return new ConcreteProductB();elsereturn NULL;}};int main(){SimpleFactory factory;Product *prdt = factory.CreateProduct(TYPEB);prdt->show();delete prdt;system("pause");return 0;}
运行结果:
ConcreteProductB
这种实现方法,存在一些问题:
1).客户程序员必须知道实际子类的名称。
2).每增加一种新产品,就需要修改工厂类。违背了开放封闭原则,并且导致程序的扩展性以及维护变得困难。
3).父类中并不知道具体要实例化哪一个具体的子类。假设:类A中需要使用类B, 而B是一个抽象父类,则A中无法知道具体要实例化哪一个B的子类,但是在A的子类D中是可以知道的。在A中,无法直接使用类似于new XXX,因为无法知道XXX代表的是哪种类。
2.工厂方法模式
于是有了工厂方法模式。它的主要特征是:定义一个用于创建对象的接口,让子类去决定实例化哪一个类。将类的实例化延迟到子类中。 仍然基于上述例子:新增一个工厂类B来生产B类型产品。此时,每个类型的工厂,生产不同类型的产品。因此,在产品生产的过程中,不再需要告诉其生产类型,而是选择对应的工厂即可。class Product{public:virtual ~Product(){};virtual void show() = 0;};class ConcreteProductA:public Product{public:void show(){ cout<<"ConcreteProductA"<<endl; }};class ConcreteProductB:public Product{public:void show() { cout<<"ConcreteProductB"<<endl;}};class Factory{public:virtual Product *CreateProduct() = 0;};class FactoryA:public Factory{public:ConcreteProductA *CreateProduct(){return new ConcreteProductA;}};class FactoryB:public Factory{public:ConcreteProductB *CreateProduct(){return new ConcreteProductB;}};int main(){FactoryA factory_a;Product *product = factory_a.CreateProduct();product->show();delete product;FactoryB factory_b;product = factory_b.CreateProduct();product->show();delete product;system("pause");return 0;}运行结果:
ConcreteProductA
ConcreteProductB
工厂方法模式,也存在一定的缺陷:
1).只要每增加一种新的产品,就需要相应的增加一个工厂,这样会产生大量的类。比起简单工厂模式,这种模式需要更多的类。这样,Factory的接口永远就无法封闭了。
(当然,也有其它方法可以解决此问题。可以通过给Factory Method传递一个类型参数,来决定具体要创建哪种Product;或者利用模板,将具体的Product类做为模板参数).
2).Factory模式存在局限性。它仅仅局限于一种类,即具体的产品类都有一个共同基类Product。如果需要为不同类型的类提供一个对象创建的接口,此方法就不行了。
3. 抽象工厂模式
因此,引出了抽象工厂模式。它的主要特点是:提供一个用来创建一系列相关联或依赖的类的接口,而无需指定它们的具体的类。举例说明:电脑做为一种产品,即有笔记本电脑(Laptop),也有台式机(Computer)。其中,每种产品又有不同的生产/实现者。因此,有下面的实现:
//抽象产品-Laptopclass ProductLaptop{public:virtual ~ProductLaptop()=0;};ProductLaptop::~ProductLaptop(){}//抽象产品-Computerclass ProductComputer{public:virtual ~ProductComputer() = 0;};ProductComputer::~ProductComputer(){}//具体产品-LenovoLaptopclass ProductLenovoLaptop:public ProductLaptop{public:ProductLenovoLaptop(){cout<<"ProductLenovoLaptop"<<endl;}};//具体产品-DellLaptopclass ProductDellLaptop:public ProductLaptop{public:ProductDellLaptop(){cout<<"ProductDellLaptop"<<endl;}};//具体产品-LenovoComputerclass ProductLenovoComputer:public ProductComputer{public:ProductLenovoComputer(){cout<<"ProductLenovoComputer"<<endl;}};//具体产品-DellComputerclass ProductDellComputer:public ProductComputer{public:ProductDellComputer(){cout<<"ProductDellComputer"<<endl;}};//抽象工厂class AbstractFactory{public:virtual ~AbstractFactory(){};virtual ProductComputer* CreateProductComputer()=0;virtual ProductLaptop* CreateProductLaptop()=0;};//具体工厂,生产lenovo品牌电脑class ConcreteFactoryLenovo:public AbstractFactory{public:ProductLaptop* CreateProductLaptop(){return new ProductLenovoLaptop();};ProductComputer* CreateProductComputer() {return new ProductLenovoComputer();};};//具体工厂,生产Dell品牌电脑class ConcreteFactoryDell:public AbstractFactory{public:ProductLaptop* CreateProductLaptop(){return new ProductDellLaptop();};ProductComputer* CreateProductComputer() {return new ProductDellComputer();};};int main(){ConcreteFactoryLenovo lenovo;lenovo.CreateProductLaptop();lenovo.CreateProductComputer();ConcreteFactoryDell dell;dell.CreateProductLaptop();dell.CreateProductComputer();system("pause");return 1;}运行结果为:
ProductLenovoLaptop
ProductLenovoComputer
ProductDellLaptop
ProductDellComputer
从上面看出,当需要创建一组对象(ProductLenovoLaptop, ProductLenovoComputer)的时候,只需要维护一个创建对象(ConcreteFactoryLenovo)即可。
4. 几种模式的区别
AbstractFactory与Factory的区别:事实上,AbstractFactory模式是为创建一组相关或依赖的对象提供创建接口,而Factory是为一类对象提供创建接口或延迟对象的创建到子类中实现。并且,可以看出AbstractFactory模式通常都是使用Factory模式实现的(ConcreteFactoryA)。
基于上面的例子:同样是Laptop和Computer,它们都可以由厂家生产,但是有不同的实现。有Lenovo和Dell两家生产出来的不同的Laptop与Computer。而负责生产Laptop与Computer就是Factory模式了。
0 0
- 工厂设计模式 factory
- 设计模式(1)-工厂模式(Factory)
- 设计模式(1)-工厂模式(Factory)
- 设计模式(1) - Factory工厂模式
- [设计模式]Factory工厂模式
- 设计模式--工厂模式Factory
- 设计模式 -- 工厂模式(Factory)
- 设计模式--工厂模式Factory
- 设计模式 - Factory工厂模式
- 设计模式(1)-工厂方法(Factory Method)
- 工厂设计模式(Factory Pattern)
- python设计模式(1)-Simple Factory(Static Factory)(简单工厂)
- 设计模式1:Simple Factory Pattern(简单工厂模式)
- 设计模式(1)-简单工厂模式(Simple Factory)
- 设计模式1 - 工厂方法模式Factory Method
- 【1】设计模式之工厂模式(Factory)
- 设计模式1-工厂方法模式(Factory Method)
- java设计模式1--工厂方法模式(Factory Method)
- uva 1422 - Processor(二分+优先队列)
- MYGUI3.2改造——与HGE结合,实现资源打包
- Android之TextView使用
- Lync 2010 部署过程中碰到的问题
- Java开发中常见的危险信号(中)
- 设计模式(1) - Factory工厂模式
- 请支持我的朋友们为我投上一票
- 随感
- mysql 分库分表
- Java正则表达式Pattern和Matcher
- 如何由XSD自动生成XML和实体类
- 【线段树】单点更新5
- Mysql分表和分区的区别
- 关于编写高性能服务器的资料汇总(Linux)