什么是享元模式 ?
运用共享技术有效地支持大量细粒度的对象。
我觉得它很像我们平常说的容器,只不过这个容器是用哈希表来存储的数据,通过键值对的形式,先把key和value值添加到哈希表里面,放入这个享元池里面,客户端通过提供的key值来获取value对象。这样的好处是什么呢?在享元池里面的key值不会重复,相同key值和value值的对象只会实例化一次,这样的话就不会产生重复的对象,避免资源的浪费。
有什么优点?
减少对象的创建,降低内存的占用,提高效率
有什么缺点?
使得系统更加复杂,为了使对象可以共享,需要将一些状态外部化,这使得程序的逻辑复杂化。
什么时候使用呢?
一个应用程序使用了大量的对象;
这些对象大多数可以外部状态时。
代码展示
场景:小菜其他私营业主做网站,需要做多个网站,但要求不太一样,有的人希望是新闻发布形式的,有人希望是博客形式的,也有还是原来的产品图片加说明形式的,而且他们都希望在费用上能大大降低。可是每个网站租用一个空间,费用上减低是不太可能的。怎么办呢?我们就可以使用享元模式。
①、享元模式
Flyweight类
abstract class Flyweight //抽象类 { public abstract void Operation(int extrinsicstate); //抽象方法 }
ConcreteFlyweight类
class ConcreteFlyweight : Flyweight //具体享元 { public ConcreteFlyweight() { } //创建此类无参构造方法 public override void Operation(int extrinsicstate) //重写Operation方法,并接收外部传来的参数 { Console.WriteLine("具体Flyweight:" + extrinsicstate); //在控制台输出结果 } }
UnsharedConcreteFlyweight类
class UnsharedConcreteFlyweight : Flyweight //不需要共享的Fleweight子类 { public override void Operation(int extrinsicstate) //重写抽象方法,并接受外部传来的参数 { Console.WriteLine("不共享的具体Flyweight:" + extrinsicstate); //在控制台输出结果 } }
FlyweightFactory类
class FlyweightFactory { private Hashtable flyweights = new Hashtable(); //创建一个哈希表 public FlyweightFactory() //创建此类的构造方法 { //初始化工厂时,先生成三个实例 flyweights.Add("X", new ConcreteFlyweight()); //往哈希表添加一个键值对X flyweights.Add("Y", new ConcreteFlyweight()); //往哈希表添加一个键值对Y flyweights.Add("Z", new ConcreteFlyweight()); //往哈希表添加一个键值对Z } public Flyweight Getflyweight(string key) { return ((Flyweight)flyweights[key]); //根据客户端请求,获得已生成的实例 } }
客户端类
int extrinsicstate = 22; //外部代码状态 FlyweightFactory f = new FlyweightFactory(); //实例化享元工厂 Flyweight fx = f.Getflyweight("X"); //创建一个网站fx对象,调用享元工厂的Getflyweight方法,将值赋给fx对象 fx.Operation(--extrinsicstate); //调用网站的Operation对象,extrinsicstate-1 Flyweight fy = f.Getflyweight("Y"); //创建一个网站fy对象,调用享元工厂的Getflyweight方法,将值赋给fy对象 fy.Operation(--extrinsicstate); //调用网站的Operation对象,extrinsicstate-1 Flyweight fz = f.Getflyweight("Z"); //创建一个网站fz对象,调用享元工厂的Getflyweight方法,将值赋给fz对象 fz.Operation(--extrinsicstate); //调用网站的Operation对象,extrinsicstate-1 Flyweight uf = new UnsharedConcreteFlyweight(); //创建一个不共享的flyweight子类 uf.Operation(--extrinsicstate); //调用网站的Operation对象,extrinsicstate-1 Console.ReadKey();