标签:def 优缺点 之间 不包含 ima 大量 枚举 already rri
运用共享技术有效地支持大量细粒度地对象。
通常情况下,面向对象技术可以增强系统地灵活性及可扩展性,在系统开发过程中,我们会不断地增加类和对象。当对象数量过多时,将会带来系统开销过高、性能下降等问题。享元模式通过共享相同或相似的对象来解决这一类问题。在介绍享元模式之前,首先要弄清楚两个概念:内部状态(Intrinsic State)和外部状态(Extrinsic State)。
抽象享元类。包含一个方法,通过这个方法flyweight可以接受外部状态。
具体享元类。实现Flyweight,对象是可共享的。
非共享享元类。享元模式并不强制共享。
享元工厂类。创建并管理Flyweight对象。
抽象享元类Flyweight,包含一个抽象方法Operation,并接受一个外部状态extrinsiState。
abstract class Flyweight
{
public abstract void Operation(int extrinsicState);
}
具体享元类ConcreteFlyweightA和ConcreteFlyweightB,实现具体的Operation方法。
class ConcreteFlyweightA : Flyweight
{
public override void Operation(int extrinsicState)
{
Console.WriteLine($"ConcreteFlyweightA->Operation[{extrinsicState}]");
}
}
class ConcreteFlyweightB : Flyweight
{
public override void Operation(int extrinsicState)
{
Console.WriteLine($"ConcreteFlyweightB->Operation[{extrinsicState}]");
}
}
享元工厂,负责维护一个享元池,用来存储具有相同内部状态的享元对象。
class FlyweightFactory
{
private Dictionary<string, Flyweight> _flyweights = new Dictionary<string, Flyweight>();
public Flyweight GetFlyweight(string key)
{
Flyweight flyweight;
if (_flyweights.ContainsKey(key))
{
Console.WriteLine("Already in the pool , use the exist one.");
flyweight = _flyweights[key];
}
else
{
switch (key)
{
case "A":
flyweight = new ConcreteFlyweightA();
break;
case "B":
flyweight = new ConcreteFlyweightB();
break;
default:
throw new Exception("Don‘t support this key");
}
_flyweights.Add(key, flyweight);
}
return _flyweights[key];
}
}
通过向工厂传入不同的key值,获取相应的享元对象。
class Program
{
static void Main(string[] args)
{
FlyweightFactory factory = new FlyweightFactory();
Flyweight fw = factory.GetFlyweight("A");
int extrinsicState = 1;
fw.Operation(extrinsicState);
Flyweight fw2 = factory.GetFlyweight("B");
fw2.Operation(extrinsicState);
extrinsicState = 2;
Flyweight fw3 = factory.GetFlyweight("A");
fw3.Operation(extrinsicState);
Console.ReadLine();
}
}
输出结果:
想象一款围棋游戏,棋盘中包含大量的黑子和白子。当然我们不能为每个棋子创建一个对象,这种设计代价太大,随着游戏的不断进行,软件占用内存会越来越大。棋子的形状、大小完全相同(内部状态),位置发生变化(外部状态)。
首先创建享元类Chessman,包含抽象方法Display,这里以x,y表示坐标位置。
abstract class Chessman
{
public abstract void Display(int x, int y);
}
创建具体享元类,为了使用方便,加入Color枚举。
class WhiteChessman : Chessman
{
public override void Display(int x, int y)
{
Console.WriteLine($"While Chessman , Position:X=>{x},Y=>{y}");
}
}
class BlackChessman : Chessman
{
public override void Display(int x, int y)
{
Console.WriteLine($"Black Chessman , Position:X=>{x},Y=>{y}");
}
}
public enum Color
{
White,
Black
}
创建Chessman工厂,维护一个享元池,如果享元池中包含请求的对象,则直接返回;如果不包含,则根据请求的颜色创建相应的对象,并添加至享元池中,最后返回给客户端。
class ChessmanFactory
{
private Dictionary<Color, Chessman> _chessman = new Dictionary<Color, Chessman>();
public Chessman GetChessman(Color color)
{
Chessman chessman;
if (_chessman.ContainsKey(color))
{
Console.WriteLine("Already in the pool , use the exist one.");
chessman = _chessman[color];
}
else
{
Console.WriteLine("new object");
switch (color)
{
case Color.White:
chessman = new WhiteChessman();
_chessman.Add(color,chessman);
break;
case Color.Black:
chessman = new BlackChessman();
_chessman.Add(color, chessman);
break;
default:
throw new Exception("Don‘t support this color");
}
}
return chessman;
}
}
客户端调用
class Program
{
static void Main(string[] args)
{
ChessmanFactory factory = new ChessmanFactory();
var chessmanA = factory.GetChessman(Color.White);
chessmanA.Display(1,1);
var chessmanB = factory.GetChessman(Color.Black);
chessmanB.Display(4, 3);
var chessmanC = factory.GetChessman(Color.White);
chessmanC.Display(5, 10);
Console.ReadLine();
}
}
一个系统中含有大量的相似或相同的对象,由于这些对象的大量使用,消耗大量的内存。
由于享元模式需要维护一个存储享元对象的享元池,所以仅当在多次重复使用享元对象时才值得使用享元模式。
标签:def 优缺点 之间 不包含 ima 大量 枚举 already rri
原文地址:https://www.cnblogs.com/Answer-Geng/p/9173513.html