GOF23设计模式之享元模式的实现

来源:互联网 发布:蒙泰软件官方网站 编辑:程序博客网 时间:2024/05/22 03:33

/** * 抽象享元类:FlyWeight,通常是一个接口或者抽象类,声明公共方法,这些方法可以向外界提供内部状态,设置 * 外部状态。 * 围棋类棋子使用享元模式 */package com.bjsxt.cn.flyWeight;
public interface ChessFlyWeight { void setColor(String color); String getColor(); void display(Coordinate c);}
/** * 具体享元类:ConcreteFlyWeight * 为内部状态提供成员变量以进行存储。在本例中指的是诸如颜色,形状,大小。 */package com.bjsxt.cn.flyWeight;
public class ConcreteChessFlyWeight implements ChessFlyWeight { private String color;
 @Override public void setColor(String color) {  this.color = color;   }
 public ConcreteChessFlyWeight(ChessColor cc) {  super();  switch (cc) {  case BLACK:   color = "black";   break;  case WHITE:   color = "white";  default:   break;  }   }
 @Override public String getColor() {    return color; }
 @Override public void display(Coordinate c) {  System.out.println("棋子的颜色是" + color);  System.out.println(c.toString());   } }
/** * 外部状态类:也就是非共享状态。UnsharedConcreteFlyWeight * 2015年4月8日20:13:14 * 在本程序中,代表的是棋子的位置坐标 */package com.bjsxt.cn.flyWeight;
public class Coordinate { private int x, y;
 public Coordinate(int x, int y) {  super();  this.x = x;  this.y = y; }  public Coordinate() { }
 public int getX() {  return x; }
 public void setX(int x) {  this.x = x; }  @Override public String toString() {    return "该棋子的坐标为" +"(" + x + ", "+ y + ")"; }
 public int getY() {  return y; }
 public void setY(int y) {  this.y = y; }  }
package com.bjsxt.cn.flyWeight;
enum ChessColor { BLACK, WHITE;};
/** * 享元工厂类:FlyWeightFactory。 * 享元工厂类的作用是创建或者获取享元对象。(一般享元模式需要和工厂模式结合在一起),享元池一般 * 设计为键值对map * 2015年4月8日20:26:12 *  */package com.bjsxt.cn.flyWeight;
import java.util.HashMap;import java.util.Map;
public class ChessFlyWeightFactory { static Map<String, ChessFlyWeight> chessesMap = new HashMap<String, ChessFlyWeight>();  /**  * 需要设置为静态返回类型。因为工厂模式多位静态工厂模式。指的是我们一般不需要工厂的对象,而直接使用  * 工厂类名来获得我们所需要的对象。这样的话,由于在静态的上下文中,不能访问非静态的成员。所以  * 我们一般要把享元池(在这里指的是map成员变量),应该设置为static  *   */ public static ChessFlyWeight getChess(ChessColor c) {  String color = null;  switch (c) {  case BLACK:   color = "black";   break;  case WHITE:   color = "white";  default:   break;  }  if (chessesMap.get(color) != null) {   return chessesMap.get(color);  } else {   /*    * 要先创建一个color颜色棋子,并且要把这个棋子放入map中。    * */   ChessFlyWeight cfw = new ConcreteChessFlyWeight(c);   chessesMap.put(color, cfw);   return cfw;  } }}
/** * 2015年4月8日20:30:55 * 测试享元工厂模式的使用: *   * 程序运行的结果如下: * 我们可以看出,我们一共生成了五个对象。但是实际打印这五个对象时,我们发现只有两个对象存在。也就是 * 享元模式的作用是这样的,如果有相同或者相似的对象,我们可以少生成对象,而是使用相同的对象。 * 这也可以我们通过打印出享元工厂类中的map容器的大小时得到了验证。 *  * 可以想象,在一盘围棋中,可以有几百个棋子,而我们在实际上只需要两个棋子对象,这会减少大量的内存消耗。 * 但是这样也会产生另外的缺点,即我们可能会生成非常多的细粒度外部状态的对象。因为每次都要new非共享 * 享元对象,因此可能会增加运行的时间。 *  * 优点: 极大减少了内存中对象的数量 相同或相似对象内存只存一份,极大地节约资源,提高系统性能 外部状态相对独立,不影响内部状态缺点: 模式较为复杂,使得程序逻辑复杂化 为了节省内存,共享了内部状态,分离出外部状态,而读取外部状态使运行时间变长。用时间换取了空间。
 */package com.bjsxt.cn.flyWeight;
import java.util.Iterator;import java.util.Map;
public class Client { public static void main(String[] args) {  ChessFlyWeight c1 = ChessFlyWeightFactory.getChess(ChessColor.BLACK);  ChessFlyWeight c2 = ChessFlyWeightFactory.getChess(ChessColor.BLACK);  ChessFlyWeight c3 = ChessFlyWeightFactory.getChess(ChessColor.WHITE);  ChessFlyWeight c4 = ChessFlyWeightFactory.getChess(ChessColor.WHITE);  ChessFlyWeight c5 = ChessFlyWeightFactory.getChess(ChessColor.WHITE);    System.out.println(c1);  System.out.println(c2);  System.out.println(c3);  System.out.println(c4);  System.out.println(c5);  Map<String, ChessFlyWeight> map = ChessFlyWeightFactory.chessesMap;  System.out.println(map.size());  for (String str : map.keySet()) {   System.out.print(str + "====");   System.out.println(map.get(str));     }  System.out.println("增加外部状态=====================");  c1.display(new Coordinate(10, 10));  c1.display(new Coordinate(20, 20));   }}
/*com.bjsxt.cn.flyWeight.ConcreteChessFlyWeight@659e0bfdcom.bjsxt.cn.flyWeight.ConcreteChessFlyWeight@659e0bfdcom.bjsxt.cn.flyWeight.ConcreteChessFlyWeight@2a139a55com.bjsxt.cn.flyWeight.ConcreteChessFlyWeight@2a139a55com.bjsxt.cn.flyWeight.ConcreteChessFlyWeight@2a139a552white====com.bjsxt.cn.flyWeight.ConcreteChessFlyWeight@2a139a55black====com.bjsxt.cn.flyWeight.ConcreteChessFlyWeight@659e0bfd增加外部状态=====================棋子的颜色是black该棋子的坐标为(10, 10)棋子的颜色是black该棋子的坐标为(20, 20)
 * */
0 0
原创粉丝点击