實現物件的複用——享元模式(三):圍棋棋子的解決方案
阿新 • • 發佈:2019-02-19
14.3 完整解決方案
為了節約儲存空間,提高系統性能,Sunny公司開發人員使用享元模式來設計圍棋軟體中的棋子,其基本結構如圖14-4所示:
在圖14-4中,IgoChessman充當抽象享元類,BlackIgoChessman和WhiteIgoChessman充當具體享元類,IgoChessmanFactory充當享元工廠類。完整程式碼如下所示:
import java.util.*;
//圍棋棋子類:抽象享元類
abstract class IgoChessman {
public abstract String getColor();
public void display() {
System.out.println("棋子顏色:" + this.getColor());
}
}
//黑色棋子類:具體享元類
class BlackIgoChessman extends IgoChessman {
public String getColor() {
return "黑色";
}
}
//白色棋子類:具體享元類
class WhiteIgoChessman extends IgoChessman {
public String getColor() {
return "白色";
}
}
//圍棋棋子工廠類:享元工廠類,使用單例模式進行設計
class IgoChessmanFactory {
private static IgoChessmanFactory instance = new IgoChessmanFactory();
private static Hashtable ht; //使用Hashtable來儲存享元物件,充當享元池
private IgoChessmanFactory() {
ht = new Hashtable();
IgoChessman black,white;
black = new BlackIgoChessman();
ht.put("b",black);
white = new WhiteIgoChessman();
ht.put("w",white);
}
//返回享元工廠類的唯一例項
public static IgoChessmanFactory getInstance() {
return instance;
}
//通過key來獲取儲存在Hashtable中的享元物件
public static IgoChessman getIgoChessman(String color) {
return (IgoChessman)ht.get(color);
}
}
編寫如下客戶端測試程式碼:
class Client {
public static void main(String args[]) {
IgoChessman black1,black2,black3,white1,white2;
IgoChessmanFactory factory;
//獲取享元工廠物件
factory = IgoChessmanFactory.getInstance();
//通過享元工廠獲取三顆黑子
black1 = factory.getIgoChessman("b");
black2 = factory.getIgoChessman("b");
black3 = factory.getIgoChessman("b");
System.out.println("判斷兩顆黑子是否相同:" + (black1==black2));
//通過享元工廠獲取兩顆白子
white1 = factory.getIgoChessman("w");
white2 = factory.getIgoChessman("w");
System.out.println("判斷兩顆白子是否相同:" + (white1==white2));
//顯示棋子
black1.display();
black2.display();
black3.display();
white1.display();
white2.display();
}
}
編譯並執行程式,輸出結果如下:
判斷兩顆黑子是否相同:true
判斷兩顆白子是否相同:true
棋子顏色:黑色
棋子顏色:黑色
棋子顏色:黑色
棋子顏色:白色
棋子顏色:白色
從輸出結果可以看出,雖然我們獲取了三個黑子物件和兩個白子物件,但是它們的記憶體地址相同,也就是說,它們實際上是同一個物件。在實現享元工廠類時我們使用了單例模式和簡單工廠模式,確保了享元工廠物件的唯一性,並提供工廠方法來向客戶端返回享元物件。