zoukankan      html  css  js  c++  java
  • 从七龙珠的角度来看设计模式之享元模式

           转载请声明:http://www.cnblogs.com/courtier/p/4290327.html

    • 人话:

           享元模式:运用共享技术解决大量对象的问题!

    • 前言:

           我所知道的设计模式最难的四大模式之一:享元模式,其他三个分别是:访问者模式,桥接模式,解释器模式!

           应用场景:JAVA 字符串内存池.(经常有些面试官问 string 是不是同一对象,其实就是考察享元模式)

           2012020619461334     

    •Flyweight

    — 描述一个接口,通过这个接口Flyweight可以接受并作用于外部状态。

    • ConcreteFlyweight

    — 实现Flyweight接口, 并为内部状态( 如果有的话) 增加存储空间。

    ConcreteFlyweight对象必须是可共享的。它所存储的状态必须是内部的;即,它必

    须独立于Concrete Flyweight对象的场景。

    • UnsharedConcreteFlyweight

    — 并非所有的Flyweight子类都需要被共享。Flyweight接口使共享成为可能,但它并不强制共享。在Flyweight对象结构的某些层次, UnsharedConcreteFlyweight对象通常

    将ConcreteFlyweight对象作为子节点(Row和Conum就是这样)。

    • FlyweightFactory

    — 创建并管理Flyweight对象。

    — 确保合理地共享Flyweight。当用户请求一个Flyweight时,FlyweightFactory对象提供一个已创建的实例或者创建一个(如果不存在的话)。

    • Client

    — 维持一个对Flyweight的引用。

    — 计算或存储一个(多个)Flyweight的外部状态。

    • 正题:

           我们知道七龙珠合并可以变成一条龙(是不是有木有)。假设,你来造这个珠子你会怎么造?肯定有一点这个珠子肯定比较贵(神也有B

           UDGET)。神嘛(不是神马),比较聪明,买了个珠子切成七份,两两可以合并(就是说龙珠一号跟龙珠二号合并成龙珠三号-Unshared

           ConcreteFlyweight的作用了)。既然,是一个大珠子切成7份,那么,从整体来看就只有一个珠子(不用买7个了欧耶,可以留下来买

           其他了O(∩_∩)O哈哈~),接下来,我们就看如何创建这个过程了。

    • 神说:第一步,我要有个接口,这个接口接受外部的龙珠-FlyWeightIn                                           

    1:龙珠的共性内容是都叫:“龙珠”。

    2:龙珠的差异在于:坐标不同,编号不同。

    神就想了,龙珠本来就是一样的,就是上面的点不同和坐标不同而已。换句话说,我拿道龙珠只是改变他的龙珠一部分属性,这个对象还是一样的。

    package FlyWeight;
    
    
    //外部状态:可变的细粒度
    //内部状态:提取出可变中不可变的细粒度
    interface FlyWeightIn {
        DragonBox operation();
    }
    • 神说:第二步,我要有个东西可以返回这个龙珠给别人用得-ConcreteFW (就是说相同的对象返回给别人修改就可以了)
    package FlyWeight;
    
    public class ConcreteFW implements FlyWeightIn{
        
        private DragonBox state;
        
        
        //传入享元的对象
        public ConcreteFW(DragonBox state) {
            this.state = state;
        }
    
        //可以对细粒度进行操作
        @Override
        public DragonBox operation() {
            // TODO Auto-generated method stub
            return state;
        }
    
    }
    • 神说:第三步,我要有个东西能合并龙珠-UnShareConcreteFW (递归合并吧)
    package FlyWeight;
    
    
    //这个类呢,不需要进行构造,因为,可以从内部状态组合成为一致的对象外部状态
    public class UnShareConcreteFW  implements FlyWeightIn{
    
        //自己组合成
        @Override
        public DragonBox operation() {
            // TODO Auto-generated method stub
            return null;
        }
    
    }
    • 神说:第四步,我要有个东西能够管理很多个大珠子-FlyWeightFactory (神的珠子不单单能够变龙,还有些可以变女人的-咳咳)
    package FlyWeight;
    
    import java.util.HashMap;
    
    public class FlyWeightFactory {
        //保持多个享元对象
        private static HashMap<String, FlyWeightIn> hashMap = new HashMap<String, FlyWeightIn>();
        
        
        public static FlyWeightIn getFlyWeight(String key)
        {        
            FlyWeightIn fw = hashMap.get(key);
            //没有享元以共性内容去做为KEY
             if(fw == null)
            {
                DragonBox box = new DragonBox();
                ConcreteFW concreteFW = new ConcreteFW(box);
                hashMap.put(key, concreteFW);
                
                fw = hashMap.get(key);
            }
            
            return fw;
        }
    }
    • 神说:通过我这个上面工厂函数去调用吧,结果如下:QQ图片20150213151010

    (源代码:https://github.com/aliencool/Design-Pattrn/tree/master/FlyWeight)

    • 结束语:

           我们可以看到上面的对象都是同一个,只是,他们有些共性粒度可以抽取出来作为键,以后就不用重复的创建大大节省内存(试试七次看能

           不能出现神龙),有问题请给我留言-谢谢。

  • 相关阅读:
    ASP.NET 无提示关闭窗口
    C# Winform程序获取外网IP地址
    使用System.Drawing.Printing 画报表。
    C# Winform调用IP地址、手机归属和身份证查询接口
    C# 获取文中文字符首字母
    C# WinForm给Button或其它控件添加快捷键响应
    C# 获取农历日期
    TSQL之插入的内容是查询出的值
    C# 获取中文星期的两种方法
    C#批量操作控件
  • 原文地址:https://www.cnblogs.com/courtier/p/4290327.html
Copyright © 2011-2022 走看看