设计模式 --> (10)享元模式
享元模式
运用共享技术有效地支持大量细粒度的对象。
享元对象能做到共享的关键是区分内蕴状态(Internal State)和外蕴状态(External State)。
内蕴状态是存储在享元对象内部并且不会随环境改变而改变。因此内蕴状态并可以共享。
外蕴状态是随环境改变而改变的、不可以共享的状态。享元对象的外蕴状态必须由客户端保存,并在享元对象被创建之后,在需要使用的时候再传入到享元对象内部。外蕴状态与内蕴状态是相互独立的。
适用性:
1.当系统中有大量的细粒度对象实例,而且这些对象实例中有一些属性是重复的情况下,考虑使用。
2.文本编辑器,输入法之类的常用应用。
优点:
1.提高了系统的效率,减小了内存的消耗。
2.减少了重复代码。
3.减少了系统的复杂度。
缺点:
1.维护共享对象和查找所需的共享对象需要花费很多时间。
举例
举个围棋的例子,围棋的棋盘共有361格,即可放361个棋子。现在要实现一个围棋程序,该怎么办呢?首先要考虑的是棋子棋盘的实现,可以定义一个棋子的类,成员变量包括棋子的颜色、形状、位置等信息,另外再定义一个棋盘的类,成员变量中有个容器,用于存放棋子的对象。
在围棋中,棋子就是大量细粒度的对象。其属性有内在的,比如颜色、形状等,也有外在的,比如 在棋盘上的位置。内在的属性是可以共享的,区分在于外在属性。因此,可以这样设计,只需定义两个棋子的对象,一颗黑棋和一颗白棋,这两个对象含棋子的内在 属性;棋子的外在属性,即在棋盘上的位置可以提取出来,存放在单独的容器中。相比之前的方案,现在容器中仅仅存放了位置属性,而原来则是棋子对象。显然, 现在的方案大大减少了对于空间的需求。
#include <iostream>
#include <vector>
using namespace std; //棋子颜色
enum PieceColor {BLACK, WHITE}; //棋子位置
struct PiecePos
{
int x;
int y;
PiecePos(int a, int b): x(a), y(b) {}
}; //棋子定义
class Piece
{
protected:
PieceColor m_color; //颜色
public:
Piece(PieceColor color): m_color(color) {}
~Piece() {}
virtual void Draw() {}
}; //黑棋
class BlackPiece: public Piece
{
public:
BlackPiece(PieceColor color): Piece(color) {}
~BlackPiece() {}
void Draw() { cout<<"绘制一颗黑棋\n"; }
}; //白棋
class WhitePiece: public Piece
{
public:
WhitePiece(PieceColor color): Piece(color) {}
~WhitePiece() {}
void Draw() { cout<<"绘制一颗白棋\n";}
}; //棋盘
class PieceBoard
{
private:
vector<PiecePos> m_vecPos; //存放棋子的位置
Piece *m_blackPiece; //黑棋棋子
Piece *m_whitePiece; //白棋棋子
string m_blackName;
string m_whiteName;
public:
PieceBoard(string black, string white): m_blackName(black), m_whiteName(white)
{
m_blackPiece = NULL;
m_whitePiece = NULL;
}
~PieceBoard() { delete m_blackPiece; delete m_whitePiece;}
void SetPiece(PieceColor color, PiecePos pos)
{
if(color == BLACK)
{
if(m_blackPiece == NULL) //只有一颗黑棋
m_blackPiece = new BlackPiece(color);
cout<<m_blackName<<"在位置("<<pos.x<<','<<pos.y<<")";
m_blackPiece->Draw();
}
else
{
if(m_whitePiece == NULL)
m_whitePiece = new WhitePiece(color);
cout<<m_whiteName<<"在位置("<<pos.x<<','<<pos.y<<")";
m_whitePiece->Draw();
}
m_vecPos.push_back(pos);
}
}; int main()
{
PieceBoard pieceBoard("A","B");
pieceBoard.SetPiece(BLACK, PiecePos(, ));
pieceBoard.SetPiece(WHITE, PiecePos(, ));
pieceBoard.SetPiece(BLACK, PiecePos(, ));
pieceBoard.SetPiece(WHITE, PiecePos(, ));
}
参考 http://blog.csdn.net/wuzhekai1985
设计模式 --> (10)享元模式的更多相关文章
- python设计模式之享元模式
python设计模式之享元模式 由于对象创建的开销,面向对象的系统可能会面临性能问题.性能问题通常在资源受限的嵌入式系统中出现,比如智能手机和平板电脑.大型复杂系统中也可能会出现同样的问题,因为要在其 ...
- 乐在其中设计模式(C#) - 享元模式(Flyweight Pattern)
原文:乐在其中设计模式(C#) - 享元模式(Flyweight Pattern) [索引页][源码下载] 乐在其中设计模式(C#) - 享元模式(Flyweight Pattern) 作者:weba ...
- 设计模式(C#)——10享元模式
推荐阅读: 我的CSDN 我的博客园 QQ群:704621321 前言 在软件开发中,当我们需要对某些对象重复创建,且最终只需要得到单一结果.如果使用一般思维,那我们将浪费很多内存空 ...
- 【GOF23设计模式】享元模式
来源:http://www.bjsxt.com/ 一.[GOF23设计模式]_享元模式.享元池.内部状态.外部状态.线程池.连接池 package com.test.flyweight; /** * ...
- 设计模式之享元模式(Flyweight)摘录
23种GOF设计模式一般分为三大类:创建型模式.结构型模式.行为模式. 创建型模式抽象了实例化过程,它们帮助一个系统独立于怎样创建.组合和表示它的那些对象.一个类创建型模式使用继承改变被实例化的类,而 ...
- 【设计模式】享元模式(Flyweight)
摘要: 1.本文将详细介绍享元模式的原理和实际代码中特别是Android系统代码中的应用. 纲要: 1. 引入享元模式 2. 享元模式的概念及优缺点介绍 3. 享元模式在Android源码中的应用 1 ...
- 【php设计模式】享元模式
享元模式其实就是共享独享模式,减少重复实例化对象的操作,从而将实例化对象造成的内存开销降到最低. 享元模式尝试重用现有的同类对象,如果未找到匹配的对象,则创建新对象.我们将通过创建 5 个对象来画出 ...
- 【UE4 设计模式】享元模式 Flyweight Pattern
概述 描述 运用共享技术有效地支持大量细粒度对象的复用.系统只使用少量的对象,而这些对象都很相似,状态变化很小,可以实现对象的多次复用. 由于享元模式要求能够共享的对象必须是细粒度对象,因此它又称为轻 ...
- JS常用的设计模式(16)—— 享元模式
享元模式主要用来减少程序所需的对象个数. 有一个例子, 我们这边的前端同学几乎人手一本<JavaScript权威指南>. 从省钱的角度讲, 大约三本就够了. 放在部门的书柜里, 谁需要看的 ...
- Head First设计模式之享元模式(蝇量模式)
一.定义 享元模式(Flyweight Pattern)主要用于减少创建对象的数量,以减少内存占用和提高性能.这种类型的设计模式属于结构型模式,它提供了减少对象数量从而改善应用所需的对象结构的方式. ...
随机推荐
- AVS、MPEG-2、H264标准文档
联合信源对AVS解码源码和相应的AVS码流.AVS码流太大,可以从http://cosoft.org.cn/projects/avsdec下载.解压avsdec_source.zip后,用VC6编译a ...
- Fresco-FaceBook推出的Android图片加载库
在Android设备上面,快速高效的显示图片是极为重要的.过去的几年里,我们在如何高效的存储图像这方面遇到了很多问题.图片太大,但是手机的内存却很小.每一个像素的R.G.B和alpha通道总共要占用4 ...
- CPLD/FPGA厂商概述 .
随着可编程逻辑器件应用的日益广泛,许多IC制造厂家涉足PLD/FPGA领域.目前世界上有十几家生产CPLD/FPGA的公司,最大的三家是:ALTERA,XILINX,Lattice,其中ALTERA和 ...
- Netty未来展望
作为<Netty权威指南(第2版)>的结尾章节,和读者朋友们一起展望下Netty的未来. 1应用范围 随着大数据.互联网和云计算的发展,传统的垂直架构逐渐将被分布式.弹性伸缩的新架构替代. ...
- 采用Global.asax的Application_BeginRequest事件过滤敏感字符
1.特殊字符过滤公共类ProcessRequest.cs using System.Web.UI; using System.Web.UI.WebControls; using System.Web. ...
- 芝麻HTTP:设置Selenium+Chrome代理
微博登录限制了错误次数···加上Cookie大批账号被封需要从Cookie池中 剔除被封的账号··· 需要使用代理··· 无赖百度了大半天都是特么的啥玩意儿???结果换成了 Google手到擒来 分分 ...
- 如何让window.open()以post请求方式调用(巧妙解法)
问题由来: 在公司遇到一个线上bug,如下 var url = 'http://106.75.31.215:8012/onlinePreview?url=' + encodeURIComponent( ...
- .Net Core从命令行读取配置文件
最近在学习博客园腾飞(jesse)的.Net Core视频教程,收益匪浅,在此作推荐 : http://video.jessetalk.cn/ 言归正传,.Net Core应用程序中如何通过命令行读取 ...
- FFMPEG 在ubuntu下的安装与使用
转载自 http://www.cnblogs.com/dwdxdy/p/3240167.html (部分一:安装) ffmpeg的安装: 1.下载源文件(以ffmpeg1.2.1为例): http:/ ...
- Hive 编程之DDL、DML、UDF、Select总结
Hive的基本理论与安装可参看作者上一篇博文<Apache Hive 基本理论与安装指南>. 一.Hive命令行 所有的hive命令都可以通过hive命令行去执行,hive命令行中仍有许多 ...