本文實例講述了Java設計模式之享元模式。分享給大家供大家參考,具體如下:
解釋一下概念:也就是說在一個系統中如果有多個相同的對象,那麼隻共享一份就可以了,不必每個都去實例化一個對象。比如說一個文本系統,每個字母定一個對象,那麼大小寫字母一共就是52個,那麼就要定義52個對象。如果有一個1M的文本,那麼字母是何其的多,如果每個字母都定義一個對像那麼內存早就爆了。那麼如果要是每個字母都共享一個對象,那麼就大大節約了資源。
在Flyweight模式中,由於要產生各種各樣的對象,所以在Flyweight(享元)模式中常出現Factory模式。 Flyweight的內部狀態是用來共享的,Flyweight factory負責維護一個對象存儲池(Flyweight Pool)來存放內部狀態的對象。 Flyweight模式是一個提高程序效率和性能的模式,會大大加快程序的運行速度.應用場合很多,下面舉個例子:
先定義一個抽象的Flyweight類:
package Flyweight;public abstract class Flyweight{public abstract void operation();}實現一個具體類:
package Flyweight;public class ConcreteFlyweight extends Flyweight{private String string;public ConcreteFlyweight(String str){string = str;}public void operation(){System.out.println("Concrete---Flyweight : " + string);}}實現一個工廠方法類:
package Flyweight;import java.util.Hashtable;public class FlyweightFactory{private Hashtable flyweights = new Hashtable();//----------------------------1public FlyweightFactory(){}public Flyweight getFlyWeight(Object obj){Flyweight flyweight = (Flyweight) flyweights.get(obj);//----------------2if(flyweight == null){//---------------------------------------------------3//產生新的ConcreteFlyweightflyweight = new ConcreteFlyweight((String)obj);flyweights.put(obj, flyweight);//--------------------------------------5}return flyweight;//---------------------------------------------------------6}public int getFlyweightSize(){return flyweights.size();}}這個工廠方法類非常關鍵,這裡詳細解釋一下:
在1處定義了一個Hashtable用來存儲各個對象;在2處選出要實例化的對象,在6處將該對象返回,如果在Hashtable中沒有要選擇的對象,此時變量flyweight為null,產生一個新的flyweight存儲在Hashtable中,並將該對象返回。
最後看看Flyweight的調用:
package Flyweight;import java.util.Hashtable;public class FlyweightPattern{FlyweightFactory factory = new FlyweightFactory();Flyweight fly1;Flyweight fly2;Flyweight fly3;Flyweight fly4;Flyweight fly5;Flyweight fly6;/** *//** Creates a new instance of FlyweightPattern */public FlyweightPattern(){fly1 = factory.getFlyWeight("Google");fly2 = factory.getFlyWeight("Qutr");fly3 = factory.getFlyWeight("Google");fly4 = factory.getFlyWeight("Google");fly5 = factory.getFlyWeight("Google");fly6 = factory.getFlyWeight("Google");}public void showFlyweight(){fly1.operation();fly2.operation();fly3.operation();fly4.operation();fly5.operation();fly6.operation();int objSize = factory.getFlyweightSize();System.out.println("objSize = " + objSize);}public static void main(String[] args){System.out.println("The FlyWeight Pattern!");FlyweightPattern fp = new FlyweightPattern();fp.showFlyweight();}}下面是運行結果:
Concrete---Flyweight : Google
Concrete---Flyweight : Qutr
Concrete---Flyweight : Google
Concrete---Flyweight : Google
Concrete---Flyweight : Google
Concrete---Flyweight : Google
objSize = 2
我們定義了6個對象,其中有5個是相同的,按照Flyweight模式的定義“Google”應該共享一個對象,在實際的對像數中我們可以看出實際的對象卻是只有2個。
總結:
Flyweight(享元)模式是如此的重要,因為它能幫你在一個複雜的系統中大量的節省內存空間。在JAVA語言中,String類型就是使用了享元模式。 String對像是final類型,對像一旦創建就不可改變。在JAVA中字符串常量都是存在常量池中的,JAVA會確保一個字符串常量在常量池中只有一個拷貝。 String a="abc",其中"abc"就是一個字符串常量。
熟悉java的應該知道下面這個例子:
String a = "hello";String b = "hello";if(a == b)System.out.println("OK");elseSystem.out.println("Error");輸出結果是:OK。可以看出if條件比較的是兩a和b的地址,也可以說是內存空間
核心總結,可以共享的對象,也就是說返回的同一類型的對像其實是同一實例,當客戶端要求生成一個對象時,工廠會檢測是否存在此對象的實例,如果存在那麼直接返回此對象實例,如果不存在就創建一個並保存起來,這點有些單例模式的意思。通常工廠類會有一個集合類型的成員變量來用以保存對象,如hashtable,vector等。在java中,數據庫連接池,線程池等即是用享元模式的應用。
更多java相關內容感興趣的讀者可查看本站專題:《Java數據結構與算法教程》、《Java操作DOM節點技巧總結》、《Java文件與目錄操作技巧匯總》和《Java緩存操作技巧匯總》
希望本文所述對大家java程序設計有所幫助。