C++设计模式(7)——享元模式

享元模式通过对象共享技术减少系统中细粒度对象的数量,降低内存开销。它在保持面向对象抽象的同时,通过区分内部状态和外部状态来实现对象的高效复用。在具体实现中,享元工厂管理并维护轻量级对象,根据需求决定复用或创建新对象。该模式适用于需要大量相似对象的场景,但会增加系统的复杂性。
摘要由CSDN通过智能技术生成

动机(Motivation)

  • 在软件系统采用纯粹对象方案的问题在于大量细粒度的对象会很快充斥在系统中,从而带来很高的运行时代价——主要指内存需求方面的代价。

  • 如何在避免大量细粒度对象问题的同时,让外部客户程序仍然能够透明地使用面向对象的方式来进行操作?

模式定义

运行共享技术有效地支持大量细粒度的对象的复用。 ——《设计模式》GoF

要点总结

  • 面向对象很好地解决了抽象性的问题,但是作为yield运行机器中的程序实体,我们需要考虑对象的代价问题, Flyweight主要解决面向对象的大量粒度问题,一般不触及面向对象的抽象性问题。

  • Flyweight采用对象共享的做法来降低系统中对象的个数,从而降低细粒度对象给系统带来的压力。在具体实现方面,要注意对象状态的处理。

  • 对象的数量太大从而导致对象内存开销加大——什么样的数量才算大?这需要我们仔细的根据具体应用情况进行评估,而不能凭空臆断。

优点:

可以极大减少内存中对象的数量,使得相同对象在内存中只保存一份,可复用性强。

缺点:

系统更加复杂,需要分离出内部状态(key)和外部状态,这使得程序的逻辑复杂化,所以应当在多次重复使用享元对象时才值得使用享元模式。

 

#include <map>
#include <iostream>
#include <string>

using namespace std;

//轻量级对象
class FlyWeight
{
public:
	FlyWeight(){}
	FlyWeight(std::string key)
	{
		m_key = key;
	}
	virtual ~FlyWeight(){}

	//value外部状态
	virtual void doSomething(int value)
	{
		cout << "doSomething key : " <<m_key<<", value:"<< value << endl;
	}

private:
	std::string m_key;                 //m_key内部状态
};


//享元工厂,管理和维护轻量级对象
class FlyWeightFactory
{
public:
	FlyWeightFactory(){}
	~FlyWeightFactory()
	{
		for (auto it = m_mapFly.begin(); it != m_mapFly.end(); it++)
		{
			if (it->second != nullptr)
			{
				delete it->second;
				it->second = nullptr;
			}
		}
	}

public:
	FlyWeight * GetFlyWeight(std::string key)
	{
		//找到则复用
		if (m_mapFly.find(key) != m_mapFly.end())
		{
			return m_mapFly[key];
		}
		//未找到则创建新的
		FlyWeight *fly = new FlyWeight(key);
		m_mapFly[key] = fly;
		return fly;
	}

private:
	std::map<std::string, FlyWeight*> m_mapFly;//共享的享元,根据key来复用或者创建新对象
};


int main()
{
	FlyWeightFactory * flyFactory = new FlyWeightFactory();

	FlyWeight * fly1 = flyFactory->GetFlyWeight("X");
	FlyWeight * fly4 = flyFactory->GetFlyWeight("X");

	FlyWeight * fly2 = flyFactory->GetFlyWeight("Y");
	FlyWeight * fly3 = flyFactory->GetFlyWeight("Z");

	fly1->doSomething(1);
	fly2->doSomething(3);
	fly4->doSomething(2);

	delete flyFactory;
}

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值