設計模式 十二 享元模式

2021-07-26 16:47:25 字數 2110 閱讀 5279

【設計模式】【一】設計六大原則

【設計模式】【二】單例模式的七種寫法

【設計模式】【三】建造者模式

【設計模式】【四】簡單工廠模式

【設計模式】【五】觀察者模式

【設計模式】【六】**模式

【設計模式】【七】裝飾模式

【設計模式】【八】外觀模式

【設計模式】【九】模版方法模式

【設計模式】【十】工廠方法模式

【設計模式】【十一】策略模式

【設計模式】【十二】享元模式

【設計模式】【十三】抽象工廠模式

享元模式是結構型設計模式的一種,是池技術的重要實現方式,它可以減少應用程式建立的物件,降低程式記憶體的占用,提高程式的效能。

定義:使用共享物件有效的支援大量細粒度的物件

要求細粒度物件,那麼不可避免地使得物件數量多且性質相近,這些物件分為兩個部分:內部狀態和外部狀態。內部狀態是物件可共享出來的資訊,儲存在享元物件內部並且不會隨環境的改變而改變。而外部狀態是物件依賴的乙個標記是隨環境改變而改變的並且不可共享的狀態。

享元模式結構圖如下圖所示。

在享元模式中有如下角色:

- flyweight:抽象享元角色,同時定義出物件的外部狀態和內部狀態的介面或者實現。

- concreteflyweight:具體享元角色,實現抽象享元角色定義的業務。

- flyweightfactory:享元工廠,負責管理物件池和建立享元物件。

某寶**賣商品,如果每個使用者下單都生成商品物件顯然會耗費很多資源,如果趕上雙11,那恐怖的訂單量會生成很多商品物件,更何況**賣的商品種類繁多,這樣就極易會產生oom。因此我們採用享元模式來對商品的建立進行優化。

抽象享元角色是乙個商品介面,它定義了showgoodsprice方法用來展示商品的**:

public

inte***ce igoods

定義類goods,它實現igoods 介面,並實現了showgoodsprice方法,如下所示。

public

class

goods

implements

igoods

@override

public

void

showgoodsprice(string version) else

if(version.equals("128g"))}}

其中name為內部狀態,version為外部狀態。showgoodsprice方法根據version的不同會列印出不同的**。

public

class goodsfactory else}}

享元工廠goodsfactory 用來建立goods物件。通過map容器來儲存goods物件,將內部狀態name作為map的key,以便標識goods物件。如果map容器中包含此key,則使用map容器中儲存的goods物件,否則就新建立goods物件,並放入map容器中。

客戶端中呼叫goodsfactory的getgoods方法來建立goods物件,並呼叫goods 的showgoodsprice方法來顯示產品的**,如下所示。

public

class client

}

執行結果為:

建立商品,key為:iphone7

**為5199元

使用快取,key為:iphone7

**為5199元

使用快取,key為:iphone7

**為5999元

從輸出看出,只有第一次是建立goods物件,後面因為key值相同,所以都是使用了物件池中的goods物件。在這個例子中,name作為內部狀態是不變的,並且作為map的key值是可以共享的。而showgoodsprice方法中需要傳入的version值則是外部狀態,他的值是變化的。

參考資料

《大話設計模式》

《設計模式之禪》

《android原始碼設計模式》

設計模式(十二)享元模式

如果系統中可能存在大量相同的物件,那麼我們可以建立快取池之類的東西,將這些重複物件進行復用。這種設計模式就是享元模式。假設有乙個遊戲,裡面需要汽車和電單車兩種載具。我們希望這些載具可以在遊戲中復用,而不是每次都建立新物件。所以這個例子就可以使用享元模式來做。首先是汽車和電單車的抽象。我們使用visi...

(十二)設計模式 享元模式

flyweight 運用共享技術有效地支援大量細粒度的物件。如果要做三個產品展示 三個部落格的 相當於是六個 類的例項,每乙個 都需要乙個對應的伺服器資源,而本質上他們都是同一套 如果 增多,例項也就隨著增多,這對伺服器的資源浪費得很嚴重,而且都不是屬於高訪問量的 如果整合到乙個 中,共享其相關的 ...

(十二)享元模式

public inte ce flyweight public class concreteflyweight implements flyweight public string getname public void setname string name public void execute...