cpp: Flyweight Pattern

发布时间 2023-05-30 21:40:48作者: ®Geovin Du Dream Park™

 

/*****************************************************************//**
 * \file   ChineseChess.h
 * \brief  享元模式 Flyweight Pattern  亦称: 缓存、Cache、Flyweight  C++ 14
 * 2023年5月30日 涂聚文 Geovin Du Visual Studio 2022 edit.
 * \author geovindu
 * \date   May 2023
 *********************************************************************/
#pragma once
#ifndef CHINESECHESS_H 
#define CHINESECHESS_H 

#include<cstring>
#include<stdbool.h>
#include<stdlib.h>
#include<iostream>
#include<malloc.h>
#include<cmath>
#include <iostream>
#include <sstream>
#include <vector>
#include <algorithm>
#include <array>
#include <functional>
#include <list>
#include <string>
#include <string.h>



using namespace std;




namespace DuJewelryFlyweightPattern
{

	/// <summary>
	/// 棋子颜色
	/// </summary>
	enum EnumColor  
	{

		/// <summary>
		/// 黑
		/// </summary>
		Black, 
		/// <summary>
		/// 白
		/// </summary>
		White   
	};
	/// <summary>
	/// 棋子位置
	/// </summary>
	struct Position 
	{

		/// <summary>
		/// x轴
		/// </summary>
		int mX;
		/// <summary>
		/// y轴
		/// </summary>
		int mY;

		/// <summary>
		/// 
		/// </summary>
		/// <param name="tmpx"></param>
		/// <param name="tmpy"></param>
		Position(int tmpx, int tmpy) :mX(tmpx), mY(tmpy) {} //构造函数
	};


	/// <summary>
	/// 棋子抽象类
	/// </summary>
	class ChineseChess
	{
	public:
		/// <summary>
		/// 做父类时析构函数应该为虚函数
		/// </summary>
		virtual ~ChineseChess() {} 

	public:
		/// <summary>
		/// 
		/// </summary>
		/// <param name="tmppos"></param>
		virtual void draw(Position tmppos) = 0;


	};

}

#endif

/*****************************************************************//**
 * \file   BlackChineseChess.h
 * \brief  享元模式 Flyweight Pattern  亦称: 缓存、Cache、Flyweight  C++ 14
 * 2023年5月30日 涂聚文 Geovin Du Visual Studio 2022 edit.
 * \author geovindu
 * \date   May 2023
 *********************************************************************/
#pragma once

#ifndef BLACKCHINESECHESS_H 
#define BLACKCHINESECHESS_H 

#include<cstring>
#include<stdbool.h>
#include<stdlib.h>
#include<iostream>
#include<malloc.h>
#include<cmath>
#include <iostream>
#include <sstream>
#include <vector>
#include <algorithm>
#include <array>
#include <functional>
#include <list>
#include <string>
#include <string.h>

#include "ChineseChess.h"



using namespace std;




namespace DuJewelryFlyweightPattern
{

	/// <summary>
	/// 黑色棋子
	/// </summary>
	class BlackChineseChess:public ChineseChess
	{
	public:

		/// <summary>
		/// 
		/// </summary>
		/// <param name="tmppos"></param>
		virtual void draw(Position tmppos)
		{
			cout << "在位置:(" << tmppos.mX << "," << tmppos.mY << ")处绘制了一个黑色中国象棋棋子!" << endl;
		}



	};

}
#endif

/*****************************************************************//**
 * \file   WhiteChineseChess.h
 * \brief  享元模式 Flyweight Pattern  亦称: 缓存、Cache、Flyweight  C++ 14
 * 2023年5月30日 涂聚文 Geovin Du Visual Studio 2022 edit.
 * \author geovindu
 * \date   May 2023
 *********************************************************************/
#pragma once

#ifndef WHITECHINESECHESS_H 
#define WHITECHINESECHESS_H 

#include<cstring>
#include<stdbool.h>
#include<stdlib.h>
#include<iostream>
#include<malloc.h>
#include<cmath>
#include <iostream>
#include <sstream>
#include <vector>
#include <algorithm>
#include <array>
#include <functional>
#include <list>
#include <string>
#include <string.h>

#include "ChineseChess.h"

using namespace std;




namespace DuJewelryFlyweightPattern
{

	/// <summary>
	/// 白色棋子
	/// </summary>
	class WhiteChineseChess:public ChineseChess
	{
	public:
		/// <summary>
		/// 
		/// </summary>
		/// <param name="tmppos"></param>
		virtual void draw(Position tmppos)
		{
			cout << "在位置:(" << tmppos.mX << "," << tmppos.mY << ")处绘制了一个白色中国象棋棋子!" << endl;
		}


	};
}

#endif


/*****************************************************************//**
 * \file   FactoryChineseChess.h
 * \brief  享元模式 Flyweight Pattern  亦称: 缓存、Cache、Flyweight  C++ 14
 * 2023年5月30日 涂聚文 Geovin Du Visual Studio 2022 edit.
 * \author geovindu
 * \date   May 2023
 *********************************************************************/
#pragma once
#ifndef FACTORYCHINESECHESS_H 
#define FACTORYCHINESECHESS_H 

#include<cstring>
#include<stdbool.h>
#include<stdlib.h>
#include<iostream>
#include<malloc.h>
#include<cmath>
#include <iostream>
#include <sstream>
#include <vector>
#include <algorithm>
#include <array>
#include <functional>
#include <list>
#include <string>
#include <string.h>
#include <map>


#include "ChineseChess.h"
#include "WhiteChineseChess.h"
#include "BlackChineseChess.h"

using namespace std;




namespace DuJewelryFlyweightPattern
{

	/// <summary>
	/// 创建棋子的工厂
	/// </summary>
	class FactoryChineseChess
	{
	public:
		/// <summary>
		/// 析构函数
		/// </summary>
		~FactoryChineseChess() 
		{
			//释放内存
			for (auto iter = m_FlyWeihgtMap.begin(); iter != m_FlyWeihgtMap.end(); ++iter)
			{
				ChineseChess* tmpfw = iter->second;
				delete tmpfw;
			}
			m_FlyWeihgtMap.clear();//这句其实可有可无
		}
	public:
		/// <summary>
		/// 获取享元对象,也就是获取被共享的棋子对象
		/// </summary>
		/// <param name="tmpcolor"></param>
		/// <returns></returns>
		ChineseChess* getFlyWeight(EnumColor tmpcolor) 
		{
			auto iter = m_FlyWeihgtMap.find(tmpcolor);
			if (iter == m_FlyWeihgtMap.end())
			{
				//没有该享元对象,那么就创建出来
				ChineseChess* tmpfw = nullptr;
				if (tmpcolor == Black) //黑子 
				{
					tmpfw = new BlackChineseChess();
				}
				else //白子
				{
					tmpfw = new WhiteChineseChess();
				}
				m_FlyWeihgtMap.insert(make_pair(tmpcolor, tmpfw));//以棋子颜色枚举值为key,增加条目到map中			
				return tmpfw;
			}
			else
			{
				return iter->second;
			}
		}
	private:
		/// <summary>
		/// 在文件头增加#include <map>
		/// </summary>
		std::map<EnumColor, ChineseChess*> m_FlyWeihgtMap; //用map容器来保存所有的享元对象,一共就两个享元对象(黑色棋子一个,白色棋子一个)


	};

}
#endif

/*****************************************************************//**
 * \file   GameOfGo.h
 * \brief  享元模式 Flyweight Pattern  亦称: 缓存、Cache、Flyweight  C++ 14
 * 2023年5月30日 涂聚文 Geovin Du Visual Studio 2022 edit.
 * \author geovindu
 * \date   May 2023
 *********************************************************************/
#pragma once
#ifndef GAMEOFGO_H 
#define GAMEOFGO_H 

#include<cstring>
#include<stdbool.h>
#include<stdlib.h>
#include<iostream>
#include<malloc.h>
#include<cmath>
#include <iostream>
#include <sstream>
#include <vector>
#include <algorithm>
#include <array>
#include <functional>
#include <list>
#include <string>
#include <string.h>
#include <map>

#include "ChineseChess.h"

using namespace std;




namespace DuJewelryFlyweightPattern
{

	/// <summary>
	/// 棋子
	/// </summary>
	class GameOfGo
	{

	public:
		/// <summary>
		/// 构造函数
		/// </summary>
		/// <param name="tmpcolor"></param>
		/// <param name="tmppos"></param>
		GameOfGo(EnumColor tmpcolor, Position tmppos) :mColor(tmpcolor), mPos(tmppos) {}
		/// <summary>
		/// 棋子的绘制
		/// </summary>
		void draw() 
		{
			if (mColor == Black)
			{
				cout << "在位置:(" << mPos.mX << "," << mPos.mY << ")处绘制了一个黑色中国围棋棋子!" << endl;
				//这里可以是一系列用于具体绘制的代码......
			}
			else
			{
				cout << "在位置:(" << mPos.mX << "," << mPos.mY << ")处绘制了一个白色中国围棋棋子!" << endl;
				//这里可以是一系列用于具体绘制的代码......
			}
		}
	private:
		/// <summary>
		/// 棋子颜色
		/// </summary>
		EnumColor  mColor;  
		/// <summary>
		/// 棋子位置
		/// </summary>
		Position mPos; //


	};

}

#endif

/*****************************************************************//**
 * \file   GeovinDu.h
 * \brief  享元模式 Flyweight Pattern  亦称: 缓存、Cache、Flyweight  C++ 14
 * 2023年5月30日 涂聚文 Geovin Du Visual Studio 2022 edit.
 * \author geovindu
 * \date   May 2023
 *********************************************************************/
#pragma once
#ifndef GEOVINDU_H 
#define GEOVINDU_H 

#include<cstring>
#include<stdbool.h>
#include<stdlib.h>
#include<iostream>
#include<malloc.h>
#include<cmath>
#include <iostream>
#include <sstream>
#include <vector>
#include <algorithm>
#include <array>
#include <functional>
#include <list>
#include <string>
#include <string.h>

#include "ChineseChess.h"
#include "WhiteChineseChess.h"
#include "BlackChineseChess.h"
#include "FactoryChineseChess.h"
#include "GameOfGo.h"


using namespace std;




namespace DuJewelryFlyweightPattern
{

	/// <summary>
	/// 
	/// </summary>
	class GeovinDu
	{

	private:

	public:

		/// <summary>
		/// 
		/// </summary>
		void displaySimple();
		/// <summary>
		/// 
		/// </summary>
		void displayGoSimple();


	};
}
#endif


/*****************************************************************//**
 * \file   GeovinDu.cpp
 * \brief  享元模式 Flyweight Pattern  亦称: 缓存、Cache、Flyweight  C++ 14
 * 2023年5月30日 涂聚文 Geovin Du Visual Studio 2022 edit.
 * \author geovindu
 * \date   May 2023
 *********************************************************************/
#include "GeovinDu.h"
using namespace std;




namespace DuJewelryFlyweightPattern
{

	/// <summary>
	/// 
	/// </summary>
	void GeovinDu::displaySimple()
	{
		DuJewelryFlyweightPattern::FactoryChineseChess* pfactory = new DuJewelryFlyweightPattern::FactoryChineseChess();

		DuJewelryFlyweightPattern::ChineseChess* p_piece1 = pfactory->getFlyWeight(DuJewelryFlyweightPattern::Black);
		p_piece1->draw(DuJewelryFlyweightPattern::Position(3, 3));//黑子落子到3,3位置 

		DuJewelryFlyweightPattern::ChineseChess* p_piece2 = pfactory->getFlyWeight(DuJewelryFlyweightPattern::White);
		p_piece2->draw(DuJewelryFlyweightPattern::Position(5, 5));//白子落子到5,5位置

		DuJewelryFlyweightPattern::ChineseChess* p_piece3 = pfactory->getFlyWeight(DuJewelryFlyweightPattern::Black);
		p_piece3->draw(DuJewelryFlyweightPattern::Position(4, 6));//黑子落子到4,6位置 

		DuJewelryFlyweightPattern::ChineseChess* p_piece4 = pfactory->getFlyWeight(DuJewelryFlyweightPattern::White);
		p_piece4->draw(DuJewelryFlyweightPattern::Position(5, 7));//白子落子到5,7位置

		//释放资源
		delete pfactory;

	}

	/// <summary>
	/// 
	/// </summary>
	void GeovinDu::displayGoSimple()
	{

		DuJewelryFlyweightPattern::GameOfGo* p_piece1 = new DuJewelryFlyweightPattern::GameOfGo(DuJewelryFlyweightPattern::Black, DuJewelryFlyweightPattern::Position(3, 3)); //黑子落子到3,3位置
		p_piece1->draw();

		DuJewelryFlyweightPattern::GameOfGo* p_piece2 = new DuJewelryFlyweightPattern::GameOfGo(DuJewelryFlyweightPattern::White, DuJewelryFlyweightPattern::Position(5, 5)); //白子落子到5,5位置
		p_piece2->draw();

		DuJewelryFlyweightPattern::GameOfGo* p_piece3 = new DuJewelryFlyweightPattern::GameOfGo(DuJewelryFlyweightPattern::Black, DuJewelryFlyweightPattern::Position(4, 6)); //黑子落子到4,6位置
		p_piece3->draw();

		DuJewelryFlyweightPattern::GameOfGo* p_piece4 = new DuJewelryFlyweightPattern::GameOfGo(DuJewelryFlyweightPattern::White, DuJewelryFlyweightPattern::Position(5, 7)); //白子落子到5,7位置
		p_piece4->draw();
		//......


		std::list<DuJewelryFlyweightPattern::GameOfGo*> piecelist; //在文件头增加#include <list>
		piecelist.push_back(p_piece1);
		piecelist.push_back(p_piece2);
		piecelist.push_back(p_piece3);
		piecelist.push_back(p_piece4);


		//释放资源
		delete p_piece1;
		delete p_piece2;
		delete p_piece3;
		delete p_piece4;


	}

}

  

调用:

/*****************************************************************//**
 * \file   ConsoleDuFlyweightPattern.cpp
 * \brief  享元模式 Flyweight Pattern  亦称: 缓存、Cache、Flyweight  C++ 14
 * 2023年5月30日 涂聚文 Geovin Du Visual Studio 2022 edit.
 * 
 * \author geovindu
 * \date   May 2023
 *********************************************************************/

// ConsoleDuFlyweightPattern.cpp : 此文件包含 "main" 函数。程序执行将在此处开始并结束。
//
#define _UNICODE

#include <iostream>
#include "GeovinDu.h"

#ifdef _DEBUG   //只在Debug(调试)模式下
#ifndef DEBUG_NEW
#define DEBUG_NEW new(_NORMAL_BLOCK,__FILE__,__LINE__) //重新定义new运算符
#define new DEBUG_NEW
#endif
#endif

using namespace std;
using namespace DuJewelryFlyweightPattern;

int main()
{
    std::cout << "Hello World!涂聚文 Geovin Du\n";

    GeovinDu geovin;
    geovin.displaySimple();

    cout << "************" << endl;
    geovin.displayGoSimple();

    system("pause");

    return 0;
}

// 运行程序: Ctrl + F5 或调试 >“开始执行(不调试)”菜单
// 调试程序: F5 或调试 >“开始调试”菜单

// 入门使用技巧: 
//   1. 使用解决方案资源管理器窗口添加/管理文件
//   2. 使用团队资源管理器窗口连接到源代码管理
//   3. 使用输出窗口查看生成输出和其他消息
//   4. 使用错误列表窗口查看错误
//   5. 转到“项目”>“添加新项”以创建新的代码文件,或转到“项目”>“添加现有项”以将现有代码文件添加到项目
//   6. 将来,若要再次打开此项目,请转到“文件”>“打开”>“项目”并选择 .sln 文件
#define UNICODE

  

输出:

Hello World!涂聚文 Geovin Du
在位置:(3,3)处绘制了一个黑色中国象棋棋子!
在位置:(5,5)处绘制了一个白色中国象棋棋子!
在位置:(4,6)处绘制了一个黑色中国象棋棋子!
在位置:(5,7)处绘制了一个白色中国象棋棋子!
************
在位置:(3,3)处绘制了一个黑色中国围棋棋子!
在位置:(5,5)处绘制了一个白色中国围棋棋子!
在位置:(4,6)处绘制了一个黑色中国围棋棋子!
在位置:(5,7)处绘制了一个白色中国围棋棋子!
请按任意键继续. . .