JAVA設計模式之享元模式
概念:
在一個系統中如果有多個相同的對象,那麼只共享一份就可以了,不必每個都去實例化一個對象。比如說一個文本系統,每個字母定一個對象,那麼大小寫字母一共就是52個,那麼就要定義52個對象。如果有一個1M的文本,那麼字母是何其的多,如果每個字母都定義一個對象那麼內存早就爆了。那麼如果要是每個字母都共享一個對象,那麼就大大節約了資源。
在Flyweight模式中,由於要產生各種各樣的對象,所以在Flyweight(享元)模式中常出現Factory模式。Flyweight的內部狀態是用來共享的,Flyweight factory負責維護一個對象存儲池(Flyweight Pool)來存放內部狀態的對象。Flyweight模式是一個提高程序效率和性能的模式,會大大加快程序的運行速度.
享元模式以共享的方式高效的支持大量細粒度對象的重用。
享元模式能做到共享的關鍵是區分內部狀態和外部狀態。內部狀態:可以共享,不會隨環境變化而變化;外部狀態:不可以共享,會隨環境變化而改變。
角色
-FlyweightFactory享元工廠類:創建並管理享元對象,享元池一般設計成鍵值對
-Flyweight抽象享元類:通常是一個接口或抽象類,聲明公共方法,這些方法可以向外界提供對象的內部狀態,設置外部狀態。
-ConcreteFlyWeight具體享元類:爲內部狀態提供成員變量進行存儲
-UnsharedConcreteFlyWeight非共享享元類:不能被共享的子類可以設計爲非共享享元類
類圖
應用
享元模式由於其共享特性,可以在任何“池”中操作,比如:線程池、數據庫連接池。
String類的設計也是享元模式。
代碼
Flyweight抽象享元類,具體享元類
//Flyweight抽象享元類
public interface ChessFlyWeight {
void setColor(String color);
String getColor();
void display(Coordinate c);
}
//ConcreteFlyWeight具體享元類
class ConcreteChess implements ChessFlyWeight {
private String color;
public ConcreteChess(String color) {
super();
this.color = color;
}
@Override
public void setColor(String color) {
}
@Override
public String getColor() {
return color;
}
@Override
public void display(Coordinate c) {
System.out.println("color: " + color);
System.out.println("coordinate: " + c.getX() + " " + c.getY());
}
}
外部狀態UnsharedConcreteFlyWeight
//外部狀態UnsharedConcreteFlyWeight
public class Coordinate {
private int x, y;
public Coordinate(int x, int y) {
this.x = x;
this.y = y;
}
public int getX() {
return x;
}
public void setX(int x) {
this.x = x;
}
public int getY() {
return y;
}
public void setY(int y) {
this.y = y;
}
}
享元工廠類
// 享元工廠類
public class ChessFlyWeightFactory {
// 享元池
private static Map
總結
優點
- 極大的減少內存對象的數量;
- 相同或相似的對象內存只存一份,極大的節約資源,提高系統性能;
- 外部狀態相對獨立,不影響內部狀態
缺點
1. 模式較複雜,使程序邏輯複雜化
2. 爲了節省內存,共享內部狀態,分離外部狀態,而讀取外部狀態使運行時間變長。用時間換取空間。