当前位置: 首页 > news >正文

C++设计模式_结构型模式_享元模式Flyweight

本篇文章记录享元模式。
享元(Flyweight)模式也称蝇量模式,是一种结构型模式,解决的是面向对象程序设计的性能问题。所谓享元就是被共享的单元或被共享的对象,其英文名 Flyweight 是“轻量的性能问题。其设计思想是:当需要某个对象时,尽量共用已经创建出的同类对象,从而避免频繁使用new创建同类或者相似的对象;在同类对象数量非常多的情况下,可以达到节省内存占用以及提升程序运行效率的目的。蝇量这个词也同样表示通过减少不必要的对象创建以减小系统运行时的负荷。

从一个典型的范例开始

在这里插入图片描述
围棋有19*19个格子,一共361个交叉点,本例子中只绘制棋子,代码如下:

    enum class Color{Black,White};struct Position{Position(int x, int y) : x(x),y(y){}int x;int y;};class ChessPiece{public:ChessPiece(Color color, Position position): m_color(color),m_position(position){}void draw(){cout << "位置:" << m_position.x << "  " << m_position.y<< "   颜色:" << (m_color == Color::Black ?  "黑色" : "白色") << endl;}private:Color m_color;Position m_position;};void test(){ChessPiece* p1 = new ChessPiece(Color::Black, Position(1, 1));p1->draw();ChessPiece* p2 = new ChessPiece(Color::Black, Position(2, 2));p2->draw();ChessPiece* p3 = new ChessPiece(Color::White, Position(3, 3));p3->draw();ChessPiece* p4 = new ChessPiece(Color::White, Position(4, 4));p4->draw();/*位置:1  1   颜色:黑色位置:2  2   颜色:黑色位置:3  3   颜色:白色位置:4  4   颜色:白色*/
}	

随着棋局不断进行,不难想象,每落下一颗棋子,就要创建一个ChessPiece 对象,程序中将会创建越来越多的ChessPiece对象,而这些对象之间除了颜色和位置不同,其余的都相同。这样看起来,只需要创建一颗代表白色和黑色的棋子就行,借助这两颗棋子来表示其他棋子,这就是享元模式的设计思想,代表黑色棋子和白色棋子的对象称为享元对象。
下面使用享元模式改造上面的代码:

    enum class Color{Black,White};struct Position{Position(int x, int y) : x(x), y(y){}int x;int y;};class ChessPiece{public:virtual ~ChessPiece() // 虚析构{}virtual void draw(Position pos) = 0;};class BlackPiece : public ChessPiece{public:virtual void draw(Position pos) override{cout << "BlackPiece" << pos.x << "," << pos.y << endl;}};class WhitePiece : public ChessPiece{public:virtual auto draw(Position pos) -> void override{cout << "WhitePiece" << pos.x << "," << pos.y << endl;}};class PieceFactory{public:virtual ~PieceFactory(){for (auto it = m_map.begin(); it != m_map.end(); ++it){delete it->second;}}// 获取蝇量,根据颜色值来获取ChessPiece* getFlyWeight(Color color){std::map<Color, ChessPiece*>::iterator it = m_map.find(color);if (it != m_map.end()){return it->second;}else{ChessPiece* tmp = (color == Color::Black ? static_cast<ChessPiece*>(new BlackPiece()) : static_cast<ChessPiece*>( new WhitePiece()));m_map[color] = tmp;  // 将新创建的对象存储到享元池中return tmp;          // 返回新创建的对象}}private:std::map<Color, ChessPiece*> m_map; // 享元池};void test(){PieceFactory* factory = new PieceFactory();ChessPiece* p1 = factory->getFlyWeight(Color::Black);p1->draw(Position(1, 1));ChessPiece* p2 = factory->getFlyWeight(Color::White);p2->draw(Position(2, 2));/*BlackPiece1,1WhitePiece2,2*/delete factory;}

上边的代码使用Map来保存黑色和白色棋子,这个map称为享元池。

引入享元(Flyweight)模式

该模式避免了程序中出现大量相同或者相似的对象,通过共享对象的方式实现相似对象的重用。
定义: 运用共享技术有效地支持大量细粒度的对象(的复用)。
**内部状态:**存储在享元对象内部,一直不会发生改变的状态。这种状态可以被共享。
**外部状态:**随着外部环境和各种动作因素的改变而发生改变的状态,这种状态不可以被共享。
**享元模式的目的:**减少对象数量,节省内存,提高程序运行效率。
在这里插入图片描述
享元模式的三种角色:
1 抽象享元类:ChesePiece类,通常是一个接口或者抽象类。
2 具体享元类:抽象享元类的子类,用这些类创建的对象就是享元对象,有时候也可以考虑以单件类实现享元对象。
3 享元工厂类:用创建并管理享元对象,该类中存在一个享元池存放享元对象。

享元使用场景

1 程序中存在大量相同或者相似对象造成内存大量消耗。
2 对象的大部分状态都是或者都可以转变为外部状态,通过参数传入到对象中。

http://www.dtcms.com/a/478587.html

相关文章:

  • 网站备案名称能重复吗微官网怎么制作
  • SpringBoot + MyBatis 注解开发入门实践
  • Java EE初阶--多线程
  • 深入理解梯度消失:从DNN到RNN的全面解析与解决方案
  • 南京电子商务网站开发公司石油化工工程建设人才招聘网站
  • 大数据实战:Python+Flask 汽车数据分析可视化系统(爬虫+线性回归预测+推荐 源码+文档)✅
  • 算法8.0
  • 网站左侧导航栏设计一个网站的建设要经过哪几个阶段
  • Java-Linux环境下查看JDK安装路径
  • 嘉立创学习
  • QML学习笔记(三十四)QML的GroupBox、RadioButton
  • AI Agent 的技术架构、产业赋能与治理挑战研究 —— 基于 2024-2025 年技术突破与应用实践的分析
  • 设计美观网站有哪些辽宁网站建设价位
  • vtkFillHolesFilter——3D网格补孔的“一键修复”工具,从原理到避坑
  • 网站建设完整代码深圳开公司流程及费用
  • Vue3为什么选择用Vite?使用指南与优势解析
  • 【STL】set容器(2336.无限集中的最小数字)
  • 第一章 计算机系统概论1
  • Cannot invoke “String.length()“ because “<parameter1>“ is null
  • H5使用环信实现视频或语音通话
  • SMTPman高效稳定的smtp服务器使用指南解析
  • 《Qt应用开发》笔记p3
  • Java-148 深入浅出 MongoDB 聚合操作:$match、$group、$project、$sort 全面解析 Pipeline 实例详解与性能优化
  • Oops 概念
  • 用老域名做新网站 权重怎么传递哈尔滨网站建设公司哪家好
  • Servlet内存马
  • 为什么要使用反射举例
  • python开发生态及学习路线和应用领域都有哪些
  • bk7258 交叉编译libzip-1.11.4
  • 汽车级mosfet的应用场景