一、定义
定义:提供了减少对象数量从而改善应用所需的对象结构的方式(减少对象的创建,减少内存的占用,提供性能)
运用共享技术有效地支持大量细粒度的对象
类型:结构型
二、适用场景
1、常常应用于系统底层的开发,以便解决系统的性能问题。
2、系统有大量相似对象、需要缓冲池的场景
三、优点
减少对象的创建,降低内存中对象的数量,降低系统的内存,提高效率
减少内存之外的其他资源占用(如New对象创建需要时间的减少)
四、缺点
关注内/外部状态、关注线程安全问题
使系统、程序的逻辑复杂化
五、扩展
1、内部状态
在享元对象的内部,并且不会随着环境的改变而改变的共享部分。
2.外部状态
在享元对象的外部,随着环境改变而改变的
六、相关设计模式
1、享元模式和代理模式
如果生成的代理类,生成和花费的时间比较多,那么可以使用享元模式提高程序的处理速度。
七、Codeing(场景:领导要求部门经理做报告)
1. 创建Employee 接口
public interface Employee {
void report();
}
2. 创建Manager 类
public class Manager implements Employee {
private String department;
private String reportContent;
//头衔
private String title = "部门经理";
public Manager(String department) {
this.department = department;
}
public void setReportContent(String reportContent) {
this.reportContent = reportContent;
}
@Override
public void report() {
System.out.println(reportContent);
}
}
这里department依赖外部传入,也就是外部状态。
title是头衔,不会改变,也就是内部状态。
3.创建EmployeeFactory 工厂类。里面有一个内部容器EMPLOYEE_MAP 。 如果没有创建Manager实例,则创建,并保存在EMPLOYEE_MAP 。
如果已经创建,则在EMPLOYEE_MAP 中取出。
public class EmployeeFactory {
private static final Map<String, Employee> EMPLOYEE_MAP = new HashMap<>();
public static Employee getManager(String department){
Manager manager = (Manager) EMPLOYEE_MAP.get(department);
if(manager == null){
manager = new Manager(department);
System.out.print("创建部门经理:" + department);
String reportConent = department + ":此次报告的内容是。。。";
manager.setReportContent(reportConent);
System.out.println(" 创建报告:" + reportConent);
EMPLOYEE_MAP.put(department,manager);
}
return manager;
}
}
4、创建测试类
public class Test
{
private final static String departments[] = {"RD","QA","PM"};
public static void main(String[] args) {
for(int i = 0; i < 10 ; i++){
String department = departments[(int)(Math.random() * departments.length)];
Manager manager = (Manager) EmployeeFactory.getManager(department);
manager.report();
}
}
}
5. UML图

八、在源码中的应用
1、Integer类valueOf方法(Long类的valueOf方法)
public static Integer valueOf(int var0) {
assert Integer.IntegerCache.high >= 127;
return var0 >= -128 && var0 <= Integer.IntegerCache.high?Integer.IntegerCache.cache[var0 + 128]:new Integer(var0);
}