享元模式-设计模式

动机

  1. 在软件系统采用纯粹对象方案的问题在于大量细粒度的对象会很快充斥在系统中,从而带来很高的运行时代价—主要指内存需求方面的代价。
  2. 如何在避免大量细粒度对象问题的同时,让外部客户程序仍然能够透明地使用面向对象的方式来进行操作?

模式定义

运用共享技术有效地支持大量细粒度的对象。
享元:共享元对象,使用了对象池的概念,把一系列对象放入对象容器中。

类图

在这里插入图片描述

总结

  1. 面向对象很好的解决了抽象性的问题,但是作为一个运行在机器中的程序实体,我们需要考虑对象的代价问题。Flyweight主要解决面向对象的代价问题,一般不触及面向对象的抽象性问题。
  2. Flyweight采用对象共享的做法来降低系统中对象的个数,从而降低细粒度对象给系统带来的内存压力。在具体实现方面,要注意对象状态的处理。
  3. 对象的数量太大从而导致对象内存开销加大—什么样的数量才算大?这需要我们仔细的根据具体应用情况进行评估,而不能凭空臆断。

实例

场景:
通过字体的显示问题,来描述享元模式的问题,考虑的字体是非常细粒度的对象,同时也是大量存在的,使用享元模式可以提高程序的性能。
注意享元模式和单例模式强调的是性能,不强调抽象,因此我们会看到类中会有具体的类,没有依赖抽象,通常比较紧耦合。

  1. 定义字体接口和具体的字体类
public interface IFont {
    void display();
}
public class SongFont implements IFont{
    private int size;

    @Override
    public void display() {
        System.out.println("Song ti display");
    }
}
  1. 定义字体工厂,核心是类中的对象池技术,对象池是实现共享的保证。
/**
 * 不考虑多线程问题
 */
public class FontFactory {
    // 享元模式的核心就是对象池
    private volatile Map<String, IFont> fontMap = new HashMap<>();

    public IFont getFont(final String key) {
        if (fontMap.get(key) == null) {
            fontMap.put(key, new SongFont());
        }
        return fontMap.get(key);
    }
}
  1. 客户端调用类,分别获取同一种字体,查看hashcode是相同的,证明使用的是同一个对象。
public class Client {
    public static void main(String[] args) {
        FontFactory fontFactory = new FontFactory();
        IFont font = fontFactory.getFont("song");
        System.out.println(font.hashCode());
        font.display();
        IFont font1 = fontFactory.getFont("song");
        System.out.println(font.hashCode());
    }
}
// 打印信息
1872034366
Song ti display
1872034366
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

融极

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值