工厂模式是属于创建模式, 大体可以分为三种,简单的工厂模式, 工厂方法模式, 抽象工厂模式
一:简单工厂模式
-
// 简单工厂模式
-
// 优点, 简单
-
// 缺点, 当需要增加新的类的时候, 需要修改工厂类, 违反开发封闭的原则, 软件实体(类, 函数, 模块)
-
// 可以扩展, 最好不要修改, 可以使用factory methond 去优化
-
#include<iostream>
-
using namespace std;
-
-
enum PTYPE { PRODUCT_A, PRODUCT_B };
-
class Product {
-
public:
-
virtual ~Product() {};
-
virtual void show() = 0;
-
};
-
-
class ProductA : public Product {
-
public:
-
void show() {
-
cout << "product a\n";
-
}
-
};
-
-
class ProductB : public Product {
-
public:
-
void show() {
-
cout << "product b\n";
-
}
-
};
-
-
class Factory {
-
public:
-
Product* Create(PTYPE type) {
-
if (type == PRODUCT_A) {
-
return new ProductA();
-
} else if (type == PRODUCT_B) {
-
return new ProductB();
-
} else {
-
return NULL;
-
}
-
}
-
-
};
-
-
int main(int argc, char* argv[]) {
-
-
Factory *pF = new Factory();
-
-
Product *pP = pF->Create(PRODUCT_A);
-
pP->show();
-
delete pF;
-
-
return 0;
-
}
二:工厂方法模式, 是对简单工厂模式的优化改进, 解决新增产品, 需要修改工厂类的问题
2.1 目的
主要是定义一个用于创建对象的接口,让子类来决定实例化哪一个类, Factory Method 让一个类的实例化延迟到了子类
2.2 使用场景:
1 当一个类不知道他必须创建的类的对象的时候
2 当一个类希望由他的子类来决定他所创建的对象时候
这个模式可以 把实例化延时到子类中决定
简单的代码
-
// 简单工厂模式
-
#include<iostream>
-
using namespace std;
-
// 实例化延迟到子类
-
-
// 缺点 , 新增产品, 就需要新增工厂, 类比较多, 可以优化-- 抽象工厂模式
-
-
enum PTYPE { PRODUCT_A, PRODUCT_B };
-
class Product {
-
public:
-
virtual ~Product() {};
-
virtual void show() = 0;
-
};
-
-
class ProductA : public Product {
-
public:
-
virtual ~ProductA() {};
-
void show() {
-
cout << "product a\n";
-
}
-
};
-
-
class ProductB : public Product {
-
public:
-
void show() {
-
cout << "product b\n";
-
}
-
};
-
-
class Factory {
-
public:
-
virtual ~Factory() {};
-
virtual Product* Create() = 0;
-
};
-
class FactoryA : public Factory {
-
public:
-
Product* Create() {
-
return new ProductA();
-
}
-
};
-
-
class FactoryB : public Factory {
-
public:
-
Product* Create() {
-
return new ProductB();
-
}
-
};
-
-
int main(int argc, char* argv[]) {
-
-
Factory *pF = new FactoryA();
-
Product *pP = pF->Create();
-
pP->show();
-
delete pF;
-
return 0;
-
}
缺点: 新增一个产品, 就需要增加一个工厂类, 如果产品比较多的话, 那么类就比较多。
三:抽象工厂模式
提供一个创建一系列相关或者互相依赖对象的接口, 而无需指定他们具体的类
-
// 简单工厂模式
-
#include<iostream>
-
using namespace std;
-
// 实例化延迟到子类
-
-
class Product {
-
public:
-
virtual ~Product() {};
-
virtual void show() = 0;
-
};
-
-
class ProductA : public Product {
-
public:
-
virtual ~ProductA() {};
-
void show() {
-
cout << "product a\n";
-
}
-
};
-
-
class Car {
-
public:
-
virtual ~Car() {};
-
virtual void show() = 0;
-
};
-
class Ben : public Car {
-
public:
-
void show() { cout << " Ben car \n"; }
-
};
-
-
class BMW : public Car {
-
public:
-
void show() { cout << " BMW car \n"; }
-
};
-
-
class ProductB : public Product {
-
public:
-
void show() {
-
cout << "product b\n";
-
}
-
};
-
-
class Factory {
-
public:
-
virtual ~Factory() {};
-
virtual Product* Create() = 0;
-
virtual Car* CreateCar() = 0;
-
};
-
class FactoryA : public Factory {
-
public:
-
Product* Create() {
-
return new ProductA();
-
}
-
-
Car* CreateCar() {
-
return new BMW();
-
}
-
};
-
-
class FactoryB : public Factory {
-
public:
-
Product* Create() {
-
return new ProductB();
-
}
-
Car* CreateCar() {
-
return new Ben();
-
}
-
};
-
-
int main(int argc, char* argv[]) {
-
-
Factory *pF = new FactoryA();
-
Product *pP = pF->Create();
-
Car *pC = pF->CreateCar();
-
pP->show();
-
pC->show();
-
delete pF;
-
return 0;
-
}
备注
手绘UML图
运行环境:
以上代码运行于linux环境, Makefile如下
-
# set CPUS for Linux or FreeBSD
-
CPUS := $(shell cat /proc/cpuinfo|grep -c processor)
-
-
-
GCC472_PATH=/usr/local/gcc-4.7.2
-
CXX := env LD_LIBRARY_PATH=$(GCC472_PATH)/lib:/usr/local/mpc/lib $(GCC472_PATH)/bin/g++
-
CXXFLAGS := -g3 -O2 -fno-strict-aliasing -Wall -Werror -fPIC \
-
-isystem /usr/local/include \
-
-isystem /usr/include
-
-
LDFLAGS := -pthread \
-
-L/usr/local/lib64/ \
-
-L/usr/local/lib/
-
RTFLAGS := \
-
-Wl,-rpath=.. \
-
-Wl,-rpath=/$(GCC472_PATH)/lib64
-
-
LIBS := -lpthread
-
-
SRC := $(wildcard *.cc)
-
OBJ := $(patsubst %.cc, %.o, $(SRC))
-
DEP := $(patsubst %.o, %.d, $(OBJ))
-
-
TARGET := main_test
-
-
all:
-
$(MAKE) -j$(CPUS) target
-
-
main_test: $(OBJ)
-
$(CXX) $^ -o $@ $(RTFLAGS) $(LDFLAGS) $(LIBS)
-
-
-
target: $(TARGET)
-
-
%.o : %.cc
-
$(CXX) -c $(CXXFLAGS) $< -o $@
-
-
%.d : %.cc
-
@$(CXX) -MM $< $(CXXFLAGS) | sed 's/$(notdir $*)\.o/$(subst /,\/,$*).o $(subst /,\/,$*).d/g' > $@
-
-
clean:
-
-rm -rf $(OBJ) $(TARGET) *.core $(DEP) *_unittest
-
-
test: all
-
./main_test
-
-
.PHONY: all target clean test
阅读(846) | 评论(1) | 转发(0) |