C++设计模式四--FactoryPattern(工厂方法模式)

来源:互联网 发布:维密摔倒后果 知乎 编辑:程序博客网 时间:2024/06/05 00:19

定义

  工厂方法模式定义了一个创建对象的接口,但由子类决定要实例化的类是哪一个。工厂方法模式把实例化推迟到子类。

要点

  1)工厂方法使用继承:把对象的创建委托给子类,子类实现工厂方法来创建对象。这样,客户程序中关于超类的代码就和子类对象创建代码解耦了。
  2)将创建对象的代码集中在一个对象或方法中,可以避免代码的重复,并且更方便以后的维护。这意味着客户在实例化对象时,只会依赖于接口,而不是具体的类。
  3)利用工厂方法创建对象时需要扩展一个类,并覆盖他的工厂方法。

类图

这里写图片描述

PizzaStore:创建者(creator)类,这是抽象创建者。它定义了一个抽象的工厂方法,让子类实现此方法制造产品。
NYPizzaStore/ChicagoPizzaStore:能够生产产品的类,即具体创建者,每个类都实现createPizza()方法,来达到创建不同产品的目的。
Pizza:产品接口。

示例

  下面实现一个披萨加盟的的模型。纽约和芝加哥各有一家披萨加盟店,他们有各自的工厂,同一款披萨会有不同的做法。

Pizza.h

#ifndef PIZZA_H#define PIZZA_H#include <iostream>#include <string>#include <list>using namespace std;namespace Factory {// 披萨超类class Pizza {protected:    string m_name;    string m_dough;    string m_sauce;    list<string> m_toppings;public:    Pizza() {}    virtual ~Pizza() {}    virtual void prepare()    {        cout << "Preparing " << m_name << endl;        cout << "Tossing dough..." << endl;        cout << "Adding sauce..." << endl;        cout << "Adding toppings:" << endl;        list<string>::iterator i;        for (i=m_toppings.begin(); i!=m_toppings.end(); i++) {            cout << *i << endl;        }    }    virtual void bake()     {        cout << "Bake for 25 minutes at 350" << endl;    }       virtual void cut()     {        cout << "Cutting the pizza into diagonal slices" << endl;    }    virtual void box()    {        cout << "Place pizza in official PizzaStore box" << endl;    }    virtual string getName()    {        return m_name;    }};class NYStyleCheesePizza : public Pizza{public:    NYStyleCheesePizza()    {        this->m_name = "NY Style Sauce and Cheese Pizza";        this->m_dough = "Thin Crust Dough";        this->m_sauce = "Marinara Sauce";        this->m_toppings.push_back("Grated");        this->m_toppings.push_back("Reggiano");        this->m_toppings.push_back("Cheese");    }};class NYStylePepperoniPizza : public Pizza{public:    NYStylePepperoniPizza()    {        this->m_name = "NY Style Pepperoni Pizza";        this->m_dough = "Pepperoni Dough";        this->m_sauce = "Pepperoni Sauce";        this->m_toppings.push_back("Grated_p");        this->m_toppings.push_back("Reggiano_p");        this->m_toppings.push_back("Cheese_p");    }};class NYStyleClamPizza : public Pizza {public:    NYStyleClamPizza()    {        this->m_name = "NY Style Clam Pizza";        this->m_dough = "Clam Dough";        this->m_sauce = "Clam Sauce";        this->m_toppings.push_back("Grated_c");        this->m_toppings.push_back("Reggiano_c");        this->m_toppings.push_back("Cheese_c");    }};class NYStyleVeggiePizza : public Pizza{public:    NYStyleVeggiePizza()    {        this->m_name = "NY Style Veggie Pizza";        this->m_dough = "Veggie Dough";        this->m_sauce = "Veggie Sauce";        this->m_toppings.push_back("Grated_v");        this->m_toppings.push_back("Reggiano_v");        this->m_toppings.push_back("Cheese_v");    }};class ChicagoStyleCheesePizza : public Pizza{public:    ChicagoStyleCheesePizza()    {        this->m_name = "Chicage Style Deep Dish Cheese Pizza";        this->m_dough = "Extra Thick Crust Dough";        this->m_sauce = "Plum Tomato Sauce";        this->m_toppings.push_back("Shredded");        this->m_toppings.push_back("Mozzarella");        this->m_toppings.push_back("Cheese");    }    void cut()    {        cout << "Cutting the pizza into square slices" << endl;    }};}#endif

PizzaStore.h

#ifndef PIZZASTORE_H#define PIZZASTORE_H#include "Pizza.h"namespace Factory {// 披萨商店超类class PizzaStore{protected:    virtual Pizza* createPizza(string type) = 0;public:    PizzaStore()    {}    virtual ~PizzaStore()    {}    Pizza* orderPizza(string type)    {        Pizza* pizza = createPizza(type);        pizza->prepare();        pizza->bake();        pizza->cut();        pizza->box();        return pizza;    }};class NYPizzaStore : public PizzaStore{protected:    Pizza* createPizza(string type)     {        if ("cheese" == type) {            return new NYStyleCheesePizza();        } else if ("veggie" == type) {            return new NYStyleVeggiePizza();        } else if ("clam" == type) {            return new NYStyleClamPizza();        } else if ("pepperoni" == type) {            return new NYStylePepperoniPizza();        } else {            return NULL;        }    }};class ChicagoPizzaStore : public PizzaStore{protected:    Pizza* createPizza(string type)     {        if ("cheese" == type) {            return new ChicagoStyleCheesePizza();        } else {            return NULL;        }    }};}#endif

main.cpp

#include "PizzaStore.h"using namespace Factory;int main(){    PizzaStore* nyStore = new NYPizzaStore();    PizzaStore* chicagoStore = new ChicagoPizzaStore();    Pizza* pizza = nyStore->orderPizza("cheese");    cout << "Ethan ordered a " << pizza->getName() << endl << endl;    pizza = chicagoStore->orderPizza("cheese");    cout << "Joel ordered a " << pizza->getName() << endl;}

测试

测试结果如下:
这里写图片描述