原型模式(c++实现)

原型模式

定义

原型模式,用原型实例指定创建对象的种类,并且通过拷贝这些原型创建新的对象。

动机

  1. 资源优化场景

    类初始化需要消化非常多的资源,这个资源包括数据、硬件资源等。

  2. 性能和安全要求的场景

    通过new产生一个对象需要非常繁琐的数据准备或访问权限,则可以使用原型模式。

  3. 一个对象多个修改者的场景

    一个对象需要提供给其他对象访问,而且各个调用者可能都需要修改其值时,可以考虑使用原型模式拷贝多个对象供调用者使用。

UML类图

原型模式

  • 原型模式基类 Prototype

    • 具体原型模式类 ConcretePrototype

    里面的关键方法就是clone()方法。

源码实现

  • prototype.h
#ifndef PROTOTYPE_H
#define PROTOTYPE_H
#include<QString>

class Prototype
{
public:
    Prototype();
    virtual ~Prototype();
    virtual Prototype* clone();

    QString GetName();
    void SetName(QString name);

    int GetAge();
    void SetAge(int* age);
protected:
    QString m_Name;
    int* m_Age;
};

class ConcretePrototype : public Prototype
{
    public:
    ConcretePrototype();
    virtual ~ConcretePrototype() override;
    virtual Prototype* clone() override;
};

#endif // PROTOTYPE_H

  • prototype.cpp
#include "prototype.h"

Prototype::Prototype()
{

}

Prototype::~Prototype()
{

}

Prototype *Prototype::clone()
{
    return new Prototype(*this);
}

QString Prototype::GetName()
{
    return m_Name;
}

void Prototype::SetName(QString name)
{
    m_Name = name;
}

int Prototype::GetAge()
{
    return *m_Age;
}

void Prototype::SetAge(int* age)
{
    m_Age = age;
}

ConcretePrototype::ConcretePrototype()
{

}

ConcretePrototype::~ConcretePrototype()
{

}

Prototype *ConcretePrototype::clone()
{
    return new ConcretePrototype(*this);
}

  • main.cpp
#include <QCoreApplication>
#include <QDebug>
#include "prototype.h"

#define DELETEOBJECT(x) if(x != nullptr) { delete x; x = nullptr;}
int main(int argc, char *argv[])
{
    QCoreApplication a(argc, argv);

    int age = 25;
    Prototype* proto = new Prototype();
    proto->SetAge(&age);
    proto->SetName("虞姬");
    qDebug() << proto->GetName();
    qDebug() << proto->GetAge();

    int age1 = 35;
    Prototype* proto1 = proto->clone();
    proto1->SetAge(&age1);
    proto1->SetName("霸王");
    qDebug() << proto1->GetName();
    qDebug() << proto1->GetAge();

    DELETEOBJECT(proto);
    DELETEOBJECT(proto1);
    return a.exec();
}

  • 运行结果

"虞姬"

25

"霸王"

35

优点

原型模式的优点:

  1. 相对于new创建新对象

    首先,用new新建对象不能获取当前对象运行时的状态,其次就算new了新对象,在将当前对象的值复制给新对象,效率也不如原型模式高。

  2. 相对于拷贝构造函数

    原型模式与拷贝构造函数是不同的概念,拷贝构造函数涉及的类是已知的,原型模式涉及的类可以是未知的。

    原型模式生成的新对象可能是一个派生类。拷贝构造函数生成的新对象只能是类本身。原型模式是描述了一个通用方法(或概念),它不管是如何实现的,而拷贝构造则是描述了一个具体实现方法。

缺点

原型模式的缺点:

  1. 配备克隆方法需要对类的功能进行通盘考虑,这对于全新的类不是很难,但对于已有的类不一定很容易,特别当一个类引用不支持串行化的间接对象,或者引用含有循环结构的时候。
  2. 实现原型模式每个派生类都必须实现 Clone接口。
  3. 逃避构造函数的约束。

参考《大话设计模式》和 https://design-patterns.readthedocs.io/zh_CN/latest/index.html

posted @ 2020-04-16 18:28  鬼谷子com  阅读(947)  评论(0编辑  收藏  举报