工厂模式

工厂模式:(最终目的是生成对象)
1.简单工厂模式
2.工厂方法模式
3.抽象工厂模式

举个例子来说明(吃苹果):
(1)对于普通的情况来说,我们要走路,买苹果,洗苹果,最后可以吃到苹果。
(2)但是对于工厂模式来说,我们可以雇人(第三方)去做走路、买苹果、洗苹果这一系列的才操作,那么就不需要自己去做,自己只要做吃苹果这个目的就可以了,不必去关心苹果的来源。
所以说只要告诉工厂,我们需要做什么就可以了,不用关心对象的生成,这就是工厂模式的优势之处。

1.简单工厂模式

#include <iostream>
#include <string>

class Fruit
{
public:
	Fruit(std::string name):mname(name){}

	virtual void option() = 0;
protected:
	std::string mname;
};

class Apple : public Fruit
{
public:
	Apple(std::string name):Fruit(name){}

	void option()
	{
		std::cout << "this is an Apple!" << std::endl;
	}
};

class Banana : public Fruit
{
public:
	Banana(std::string name):Fruit(name){}

	void option()
	{
		std::cout << "this is an Banana!" << std::endl;
	}
};

class Factory
{
public:
	Fruit* createFactory(int flag)
	{
		switch (flag)
		{
		case 1:
			return new Apple("apple");
			break;
		case 2:
			return new Banana("banana");
			break;
		default:
			std::cout << "no product!" << std::endl;
			return nullptr;
			break;
		}
	}
};

int main()
{
	Factory f;
	Fruit* pf = f.createFactory(2);
	pf->option();
	return 0;
}

此时无论是苹果还是香蕉都是从同一个工厂中产出的。 那么如果此时还需要添加一条梨的产线,应该怎么办呢?
我们需要添加一个类:

class Pear : public Fruit
{
public:
	Pear(std::string name):Fruit(name){}

	void option()
	{
		std::cout << "this is an Pear!" << std::endl;
	}
};

并且要添加工厂模式中的内容:

class Factory
{
public:
	Fruit* createFactory(int flag)
	{
		switch (flag)
		{
		case 1:
			return new Apple("apple");
			break;
		case 2:
			return new Banana("banana");
			break;
		case 3:
			return new Pear("Pear");
			break;
		default:
			std::cout << "no product!" << std::endl;
			return nullptr;
			break;
		}
	}
};

我们可以看到,如果要是添加一条生产线会很麻烦,不灵活,要频繁的修改工厂的代码,这就违背了面向对象中的开放-封闭原则:
(1)开放原则
新版本可以沿用旧版本的代码
(2)封闭原则
不能修改旧版本的代码

基于此,就提出了第二种的工厂模式:

2.工厂方法模式
一个工厂生产一种产品,即有一个工厂只生产苹果,另外一个工厂只生产香蕉,如果再想生产梨,则需要再开发一个工厂,这个时候就不会影响到其他的工厂及其产品,所以此时应该将工厂写成基类。

class Fruit
{
public:
	Fruit(std::string name):mname(name){}

	virtual void option() = 0;
protected:
	std::string mname;
};

class Apple : public Fruit
{
public:
	Apple(std::string name):Fruit(name){}

	void option()
	{
		std::cout << "this is an Apple!" << std::endl;
	}
};

class Banana : public Fruit
{
public:
	Banana(std::string name):Fruit(name){}

	void option()
	{
		std::cout << "this is an Banana!" << std::endl;
	}
};
class Factory
{
public:
	Factory(std::string name):mname(name){}
	
	//创建不同功能的工厂
	virtual Fruit* createFruit() = 0;
protected:
	std::string mname;
};

//苹果工厂
class Factory_1 : public Factory
{
public:
	Factory_1(std::string name):Factory(name){}

	Fruit* createFruit()
	{
		return new Apple("Apple");
	}
};

//香蕉工厂
class Factory_2 : public Factory
{
public:
	Factory_2(std::string name):Factory(name){}

	Fruit* createFruit()
	{
		return new Banana("Banana");
	}
};

int main()
{
	Factory* pf = new Factory_1("f1");
	Fruit* ppf = pf->createFruit();
	ppf->option();
	return 0;
}

如果此时再想加梨的生产线的时候,我们只需要添加一个生产梨的工厂就可以了:

class Pear : public Fruit
{
public:
	Pear(std::string name):Fruit(name){}

	void option()
	{
		std::cout << "this is an Pear!" << std::endl;
	}
};
class Factory_3 : public Factory
{
public:
	Factory_3(std::string name):Factory(name){}

	Fruit* createFruit()
	{
		return new Pear("Pear");
	}
};

这样的话就可以解决开放-封闭原则的问题啦。

3.抽象工厂模式
如果此时我们需要生产一台电脑C,需要配件A、B来组成:
在这里插入图片描述
A1和A2、B1和B2是属于同一种配件,只是大小不同,那么A1和A2、B1和B2属于同一族,A1和B1之间具有强相关性。所以我们这样设计才可以体现出强相关性,因为只有编号对应才可以组成相应的电脑。
在这里插入图片描述

//生产A部件
class A
{
public:
	A(std::string name):mname(name){}

	virtual void option() = 0;
protected:
	std::string mname;
};

class A_1 : public A
{
public:
	A_1(std::string name):A(name){}

	void option()
	{
		std::cout << "this is A1" << std::endl;
	}
};

class A_2 : public A
{
public:
	A_2(std::string name):A(name){}

	void option()
	{
		std::cout << "this is A2" << std::endl;
	}
};

//生产B部件
class B
{
public:
	B(std::string name):mname(name){}

	virtual void option() = 0;
protected:
	std::string mname;
};

class B_1 : public B
{
public:
	B_1(std::string name):B(name){}

	void option()
	{
		std::cout << "this is B1" << std::endl;
	}
};

class B_2 : public B
{
public:
	B_2(std::string name):B(name){}

	void option()
	{
		std::cout << "this is B2" << std::endl;
	}
};

class AbstractFactory
{
public:
	AbstractFactory(std::string name):mname(name){}
	virtual A* createA() = 0;
	virtual B* createB() = 0;
protected:
	std::string mname;
};

//创建编号为1的部件
class AF1 : public AbstractFactory
{
public:
	AF1(std::string name):AbstractFactory(name){}

	A* createA()
	{
		return new A_1("a1");
	}
	B* createB()
	{
		return new B_1("b1");
	}
};

//创建编号为2的部件
class AF2 : public AbstractFactory
{
public:
	AF2(std::string name):AbstractFactory(name){}

	A* createA()
	{
		return new A_2("a2");
	}
	B* createB()
	{
		return new B_2("b2");
	}
};

int main()
{
	AbstractFactory* apf = new AF2("af2");
	A* pa = apf->createA();
	B* pb = apf->createB();
	pa->option();
	pb->option();
	return 0;
}

总结:
1.简单工厂模式–规模固定,产品不容易发生变动
就是将生产交给一个工厂,再有生产线进来的时候也是交给这个工厂,违背了开放-封闭原则

2.工厂方法模式–规模不固定,产品容易发生变动
解决开放-封闭原则,灵活性更大,一种产品对应一个工厂,可以理解成一对一的情况

3.抽象工厂模式
对于一件东西的不同组成部分,体现的主要是这些步骤之间的关联,那么才使用抽象工厂模式

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值