抽象工厂模式

  • 抽象工厂模式是围绕一个超级工厂创建其他工厂。该超级工厂是其他工厂的工厂
  • 在抽象工厂模式中,接口是负责创建一个相关对象的工厂,不需要显示指定他们的类,每个工厂都能按照工厂模式提供对象。

主要解决的问题:解决接口选择的问题
使用的时机:系统的产品有用于一个的产品族,而系统只消费其中的某一组产品
解决方法:在一个产品族里定义多个产品
关键代码:在一个工厂里聚合多个同类产品

  • 优点:
    1、当一个产品族中的多个对象被设计成一起工作时,它能保证客户端始终只使用同一个产品族中的对象;
  • 缺点:
    1、产品族扩展非常困难,要增加一个系列的某一个产品,既要在抽象的Creator里加代码,又要在具体的类里面加代码
    2、产品族扩展困难,产品等级扩展容易
    抽象工厂类图.PNG
  • 实例:
    举个例子,我们要生产一把尺子,尺子有形状和颜色两个属性,尺子的形状和颜色分别需要两个工厂完分别完成定形(形状)和涂色(颜色),其中形状又分为多种 :矩形、圆形等,颜色分为绿色、蓝色等,一把尺子只有只有一种形状和颜色。在这种情况下生产一把尺子的代码实现如下,原理框图如上图所示。
  • 代码实现
#include <iostream>
using namespace std;

enum ShapeType
{
    RECTANGLE,
    CIRCLE
};
enum ColorType
{
    GREEN,
    BLUE
};
enum Type
{
    SHAPE,
    COLOR
};

//定义一个形状类
class Shape
{
public:
    virtual void draw() = 0; //纯虚方法
};
//定义一个矩形
class Rectangle:public Shape
{
public:
    Rectangle()
    {
        cout<<"Rectangle---创建矩形对象"<<endl;
    }
    virtual void draw()
    {
        cout<<"Rectangle::draw Rectangle"<<endl;  
    }
};
//定义一个圆形
class Circle:public Shape
{
public:
    Circle()
    {
        cout << "Circle---创建圆形对象" << endl;
    }
    virtual void draw()
    {
        cout << "Circle::draw Circle" << endl;    
    }
};
//定义一个颜色类
class Color
{
public:
    virtual void fill() = 0; //纯虚方法
};
//定义一个绿色
class Green:public Color
{
public:
    Green()
    {
        cout<<"Green---创建绿色对象"<<endl;
    }
    virtual void fill()
    {
        cout<<"Green::fill Green"<<endl;  
    }
};
//定义一个蓝色
class Blue:public Color
{
public:
    Blue()
    {
        cout<<"Blue---创建蓝色对象蓝色"<<endl;
    }
    virtual void fill()
    {
        cout<<"Blue::fill Blue";    
    }
};
//定义一个抽象工厂
class AbsractFactory
{
public:
    virtual Color* getColor(ColorType type) =0; //纯虚函数
    virtual Shape* getShape(ShapeType type) =0; //纯虚函数
};
/* 注意:派生类必须实现基类的所有纯虚函数,
 *      负责派生类也就有了纯虚函数,派生类也就成了抽象类,不能被实例化
 */
//定义一个形状工厂
class ShapeFactory: public AbsractFactory
{
public:
    virtual Shape* getShape(ShapeType type)
    {
        switch(type)
        {
            case RECTANGLE: 
                return (new Rectangle());
                break;
            case CIRCLE:
                return (new Circle());
                break;
            default:
                return NULL;
                break;      
        }   
    }
    virtual Color* getColor(ColorType type)
    {
        return NULL;
    }
    
};
//定义一个色彩填充工厂
class ColorFactory:public AbsractFactory
{
public:
    virtual Color* getColor(ColorType type)
    {
        switch(type)
        {
            case GREEN: 
                return (new Green());
                break;
            case BLUE:
                return (new Blue());
                break;
            default:
                return NULL;
                break;      
        }   
    }
    virtual Shape* getShape(ShapeType type)
    {
        return NULL;
    }
    
};

//定义一个工厂生产者
class FactoryProducer
{
public:
    FactoryProducer()
    {
        cout<<"创建一个工厂"<<endl;
    }
    static AbsractFactory* getFactory(Type type)
    {
        switch(type)
        {
            case SHAPE:
                return (new ShapeFactory());
                break;
            case COLOR:
                return (new ColorFactory());
                break;
            default:
                return NULL;
                break;
                
        }
    }
};

/* 注意:派生类必须实现基类的所有纯虚函数,
 *       负责派生类也就有了纯虚函数,派生类也就成了抽象类,不能被实例化
 */
int main()
{
    // 1、创建一把形状为圆形的尺子
    /* 1.1、获取形状工厂 */
    AbsractFactory *pShapeFactory = FactoryProducer::getFactory(SHAPE);
    
    /* 1.2、获得一个形状为圆形的对象 */
    Shape *pShape = pShapeFactory->getShape(CIRCLE);
    
    /* 1.3、调用圆形对象的画笔画圆形形状 */
    pShape->draw();
    
    // 2、为尺子填充颜色:绿色
    /* 2.1、获取颜色工厂 */
    AbsractFactory *pColorFactory = FactoryProducer::getFactory(COLOR);
    
    /* 2.2、获得一个绿色对象 */
    Color *pColor = pColorFactory->getColor(GREEN);
    
    /* 2.3、调用绿色对象的染色桶填充颜色:绿色 */
    pColor->fill();
    
    
    // 1、创建一把形状为矩形的尺子
    /* 1.1、获取形状工厂 */
    pShapeFactory = FactoryProducer::getFactory(SHAPE);
    
    /* 1.2、获得一个形状为矩形的对象 */
    pShape = pShapeFactory->getShape(RECTANGLE);
    
    /* 1.3、调用矩形对象的画笔画矩形形状 */
    pShape->draw();
    
    // 2、为尺子填充颜色:蓝色
    /* 2.1、获取颜色工厂 */
    pColorFactory = FactoryProducer::getFactory(COLOR);
    
    /* 2.2、获得一个蓝色对象 */
    pColor = pColorFactory->getColor(BLUE);
    
    /* 2.3、调用蓝色对象的染色桶填充颜色:蓝色 */
    pColor->fill();
    
}

//////////////////////////运行结果////////////////////////////////////////
Circle---创建圆形对象
Circle::draw Circle
Green---创建绿色对象
Green::fill Green
Rectangle---创建矩形对象
Rectangle::draw Rectangle
Blue---创建蓝色对象蓝色
Blue::fill Blue


最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容