享元模式
享元模式:使用共享对象有效的支持大量细粒度的对象,是池技术的重要实现方式。类图:
*有时候在程序中会不可避免的使用到大量的性质相近的对象,我们把这些对象的信息分为两个部分:内部状态和外部状态。
*内部状态:对象可共享出来的信息,它们不会随环境的改变而改变但可以作为对象的附加动态信息而不必储存在具体的某个对象中,是可以共享的部分。
*外部状态:对象依赖的一个标记,随环境的改变而改变的不可共享的状态。
*Flyweight抽象享元角色:产品的抽象类,同时定义对象的外部状态和内部状态的接口或实现。
1 //抽象享元角色 2 interface Flyweight{ 3 //传入外部状态 4 public void operate(String Extrinsic); 5 }
*ConcreteFlyweight具体享元角色:具体的一个产品类,实现抽象角色定义的业务。要求是:内部状态的处理与环境无关。
1 //具体享元角色 2 class ConcreteFlyweightA implements Flyweight{ 3 private Character intrinsic; 4 //注入内部状态 5 public ConcreteFlyweightA(Character intrinsic) { 6 this.intrinsic = intrinsic; 7 } 8 @Override 9 public void operate(String Extrinsic) { 10 System.out.println("状态:"+this.intrinsic + "-" + Extrinsic); 11 } 12 }
*unsharedConcreteFlyweight不可共享的享元角色:不存在外部状态或者安全要求(线程安全)不能够使用共享技术的对象。
1 //具体的不共享的享元角色 2 class UnsharedConcreteFlyweightB implements Flyweight{ 3 private Map<Character, Flyweight> files=new HashMap<>(); 4 public void add(Character key,Flyweight fly){ 5 files.put(key, fly); 6 } 7 @Override 8 public void operate(String Extrinsic) { 9 Flyweight fly = null; 10 for (Object o : files.keySet()) { 11 fly = files.get(o); 12 fly.operate(Extrinsic); 13 } 14 } 15 }
*FlyweightFactory享元工厂:构造一个池,同时提供从池中获得对象的方法。
//享元工厂 不考虑缓存清理和线程安全 class FlyweightFactory{ //定义池 private static Map<Character, Flyweight> pool = new HashMap<>(); //享元工厂 public Flyweight factory(Character Extrinsic){ Flyweight flyweight = null; if(pool.containsKey(Extrinsic)){ //使用已有对象 flyweight = pool.get(Extrinsic); }else{ //创建新对象 flyweight = new ConcreteFlyweightA(Extrinsic); pool.put(Extrinsic, flyweight); } return flyweight; } //复合享元工厂方法 public Flyweight factory(List<Character> Extrinsic){ UnsharedConcreteFlyweightB flyweightB = new UnsharedConcreteFlyweightB(); for(Character state : Extrinsic){ flyweightB.add(state,this.factory(state)); } return flyweightB; } }
客户端代码:
1 public class Client{ 2 public static void main(String[] args) { 3 List<Character> list = new ArrayList<>(); 4 list.add('a'); 5 list.add('b'); 6 FlyweightFactory factory = new FlyweightFactory(); 7 Flyweight flyweightB_1 = factory.factory(list); 8 Flyweight flyweightB_2 = factory.factory(list); 9 System.out.println(flyweightB_1==flyweightB_2);//不共享 10 //--------------------------------------------------- 11 Flyweight flyweightA_1 = factory.factory('c'); 12 Flyweight flyweightA_2 = factory.factory('c'); 13 System.out.println(flyweightA_1==flyweightA_2);//共享 14 } 15 }
*总结:享元模式的本质就是分离与共享,分离的是状态中便与不变的部分,共享的对象中不变的部分。
*关于缓存清除和线程安全问题会后续补上。。。