设计模式——享元模式(Flyweight)

设计模式(12): 享元模式(Flyweight)
 
享元模式(Flyweight)
 
定义
     运用共享技术有效地支持大量细粒度的对象。
 
概述    
    面向对象的思想很好地解决了抽象性的问题,一般也不会出现性能上的问题。但是在某些情况下,对象的数量可能会太多,从而导致了运行时的代价。那么我们如何去避免大量细粒度的对象,同时又不影响客户程序使用面向对象的方式进行操作?
      
享元模式(Flyweight)
 
设计模式——享元模式(Flyweight)_第1张图片
 
  Flyweight类,它是所有享元类的超类或接口,通过这个接口,Flyweight可以接受并作用于外部状态。
abstract   class  Flyweight
{
    
public   abstract   void  Operation( int  extrinsicstate);
}
 
ConcreteFlyweight是继承Flyweight超类或实现Flyweight接口。并为内部状态增加存储空间。
class  ConcreteFlyweight:Flyweight
{
    
public   override   void  Operation( int   extrinsicstate)
    {
        Console.WriteLine(
" 具体Flyweight: "   + extrinsicstate);
    }
}
 
UnsharedConcreteFlyweight是指那些不需要共享的Flyweight子类,因为Flyweight接口共享成为可能,但它并不强制共享。
class  UnsharedConcreteFlyweight:Flyweight
{
    
public   override   void  Operation( int   extrinsicstate)
    {
        Console.WriteLine(
" 不共享的具体Flyweight: "   + extrinsicstate);
    }
}
 
FlyweightFactory,是一个享元工厂,用来创建并管理Flyweight对象。它主要是用来确保合理地共享Flyweight,
当用户请求一个Flyweight时,FlyweightFactory对象提供一个已创建的实例或者创建一个(如果不存在的话)
 
class  FlyweightFactory
{
    
private  Hashtable flyweights = new  Hashtable();
    
public  FlyweightFactory()
    {
        flyweights.Add(
" X " , new  ConcreteFlyweight());
        flyweights.Add(
" Y " , new  ConcreteFlyweight());
        flyweights.Add(
" Z " , new  ConcreteFlyweight());
    }
    
    
public  Flyweight GetFlyweight( string  key)
    {
        
return  ((Flyweight)flyweights[key]);
    }
}
 
客户端代码:  
static   void  Main( string [] args)
{
    
int  extrinsicstate = 22 ;
    FlyweightFactory f
= new  FlyweightFactory();
    
    Flyweight fx
= f.GetFlyweight( " X " );
    fx.Operation(
-- extrinsicstate);
    
    Flyweight fy
= f.GetFlyweight( " Y " );
    fy.Operation(
-- extrinsicstate);
    
    Flyweight fz
= f.GetFlyweight( " Z " );
    fz.Operation(
-- extrinsicstate);
    
    UnshareConcreteFlyweight uf
= new  UnshareConcreteFlyweight();
    uf.Operation(
-- extrinsicstate);
}
 
结果显示: 
具体extrinsicstate: 21
具体extrinsicstate:
20
具体extrinsicstate:
19
不共享的具体extrinsicstate:
18
 
在.NET Framework中,Hashtable是System.Collections命名空间提供的一个容器,用于处理和表现类似key/value的键值对,其中 
key通常可用来快速查找,同时key是区分大小写;value用于存储对应于key的值。Hashtable中key/value键值对均为object类型,所以Hashtable可以支持任何类型的key/value键值对.
 
二.哈希表的简单操作
 在哈希表中添加一个key/value键值对:HashtableObject.Add(key,value);
在哈希表中去除某个key/value键值对:HashtableObject.Remove(key);
从哈希表中移除所有元素: HashtableObject.Clear();
判断哈希表是否包含特定键key: HashtableObject.Contains(key);
 
 在享元对象内部并且不会随环境改变而改变的共享部分,可以称为享元对象的内部状态,而随环境改变而改变的,不可以共享的状态就是外部状态了。
享元模式可以避免大量非常相似类的开销。在程序设计中,有时需要生成大量细粒度的类实例来表示数据。如果能发现这些实例除了几个参数外基本上都是相同的,有时就能够受大幅度地减少需要实例化的类的数量。如果能把那些参数移到类实例的外面,在方法调用时将它们传递过来,就可以通过共享大幅度地减少单个实例的数目。也就是说,享元模式Flyweight执行时所需要的状态是有内部的也可能有外部的,内部状态存储于 ConcreteFlyweight对象之中,而外部对象则应该考虑由客户端对象存储或计算,当调用Flyweight对象的操作时, 将该状态传递给它。
 
设计模式——享元模式(Flyweight)_第2张图片
 
public   class  User
{
    
private   string  name;
    
public  User( string  name)
    {
        
this .name = name;
    }
    
public   string  Name
    {
        
get { return  name;}
    }
}
abstract   class  WebSite
{
    
public   abstract   void  Use(User user); // “使用”方法需要传递“用户”对象
}

class  ConcreteWebSite:WebSite
{
    
private   string  name = "" ;
    
public  ConcreteWebSite( string  name)
    {
        
this .name = name;
    }
    
public   override   void  Use(User user) // 实现“Use”方法
    {
        Console.WriteLine(
" 网站分类: " + name + “用户:” + user.name);
    }
}

class  WebSiteFatory
{
     
private  Hashtable flyweights = new  Hashtable();
     
public  WebSite GetWebSiteCategory( string  key)
     {
          
if ( ! flyweight.Containskey(key))
             flyweight.Add(key,
new  ConcreteWebSite(name));
           
return  ((WebSite)flyweights[key]);
     } 
    
public   int  GetWebSiteCount()
    {
        
return  flyweight.count;
    }
}

    
static   void  Main( string  args)
    {
        WebSiteFactory f
= new  WebSiteFactory();
        
        WebSite fx
= f.GetWebSiteCategory( " 产品展示 " );
        fx.Use(
new  User( " 小明 " ));
        
        WebSite fy
= f.GetWebSiteCategory( " 产品展示 " );
        fy.Use(
new  User( " 晓阳 " ));
        
        WebSite fz
= f.GetWebSiteCategory( " 博客 " );
        fz.Use(
new  User( " 扬帆 " ));
        
        WebSite fl
= f.GetWebSiteCategory( " 博客 " );
        fl.Use(
new  User( " 泰特 " ));   
         Console.WriteLine(
" 得到网站分类总数为{0} " ,f.GetWebSiteCount());    
    }
    
    显示结果
    网站分类:产品展示  用户:小明
    网站分类:产品展示  用户:晓阳
    网站分类:博客 用户:扬帆
    网站分类:博客 用户:泰特
    得到网站分类总数为 
2

你可能感兴趣的:(flyweight)