甜品網(wǎng)站模板/圖片外鏈在線生成網(wǎng)址
1、定義與動(dòng)機(jī)
-
概述:享元模式和單例模式一樣,都是為了解決程序的性能問題。面向?qū)ο蠛芎玫亟鉀Q了"抽象"的問題,但是必不可免得要付出一定的代價(jià)。對(duì)于通常情況來講,面向?qū)ο蟮某杀敬蠖箍梢院雎圆挥?jì)。但是某些情況,面向?qū)ο笏鶐淼某杀颈仨氈?jǐn)慎處理。
-
定義:運(yùn)用共享技術(shù)有效地支持大量細(xì)粒度的對(duì)象。
-
動(dòng)機(jī):
- 在軟件系統(tǒng)中采用純粹對(duì)象方案的問題在于大量細(xì)粒度的對(duì)象會(huì)很快充斥在系統(tǒng)中,而帶來很高的運(yùn)行時(shí)代價(jià)——主要指內(nèi)存需求方面的代價(jià)。
- 如何避免大量細(xì)粒度對(duì)象問題的同時(shí),讓外部客戶程序仍然能夠透明地使用面向?qū)ο蟮姆绞絹磉M(jìn)行操作?
-
個(gè)人理解:例如在電腦中存在大量的字體
-
首先:電腦在啟動(dòng)時(shí)不可能把所有的字體的文件渲染方式或者字體樣式都加載到內(nèi)存中,而應(yīng)該是在需要的時(shí)候去加載
-
其次:當(dāng)電腦字體需要更改時(shí)會(huì)創(chuàng)建一個(gè)字體對(duì)象,而wps/office中的字體也會(huì)有一個(gè)對(duì)象字體。
-
當(dāng)word和ppt中的字體相同時(shí),應(yīng)該是只需要?jiǎng)?chuàng)建一個(gè)對(duì)象,因?yàn)樽煮w這個(gè)東西應(yīng)該說只讀(只用來渲染,總不可能更改樣式吧),因此這兩個(gè)對(duì)象應(yīng)該使用同一個(gè)對(duì)象即可,不應(yīng)該在需要的地方就new!
-
很明顯這里也是解決一個(gè)性能問題的設(shè)計(jì)模式
-
比較常見的一個(gè)實(shí)用地方:各種池子,線程池、內(nèi)存池、連接池…,它們都應(yīng)該創(chuàng)建好需要的時(shí)候去取一個(gè)就行,用完了還回去;而不是需要的時(shí)候new一個(gè)。
-
2、享元模式
- 對(duì)于Font類創(chuàng)建出來的對(duì)象應(yīng)該只能讀,不允許修改
- FontFactory字體工廠負(fù)責(zé)取字體,如果沒有就new一個(gè)字體然后存放在一個(gè)數(shù)據(jù)結(jié)構(gòu)中(這里用無序map)
#include <iostream>
#include <unordered_map>
#include <string>
class Font{
private:// unique object keystd::string key;// object state ...
public:Font(const std::string &_key){// ...}
};class FontFactory{
private:std::unordered_map<std::string, Font*> fontPool;
public:Font *GetFont(const std::string &key){if(fontPool.find(key) == fontPool.end()){Font *font = new Font(key);fontPool.insert(std::make_pair(key, font));}return fontPool[key];}
};void process()
{FontFactory* fontFactory = new FontFactory();Font* songStyle = fontFactory->GetFont("宋體");Font* kaiStyle = fontFactory->GetFont("楷體");// ...
}
其實(shí)這里沒有設(shè)計(jì)好:
- FontFactory可以到處創(chuàng)建,可以考慮把FontFactory字體工廠做成一個(gè)單例的工廠。
- 字體獲取的多線程安全問題,準(zhǔn)確來說獲取應(yīng)該是沒有線程安全問題的,創(chuàng)建有…
3、總結(jié)
- 面向?qū)ο蠛芎玫慕鉀Q了抽象性問題,但是作為一個(gè)運(yùn)行在機(jī)器中的程序?qū)嶓w,我們需要考慮對(duì)象的代價(jià)問題。Flyweight主要解決面向?qū)ο蟮拇鷥r(jià)問題,一般不初級(jí)面向隊(duì)形的抽象性問題
- Flyweight采用對(duì)象共享的做法來降低系統(tǒng)中對(duì)象的個(gè)數(shù),從而降低細(xì)粒度對(duì)象給系統(tǒng)帶來的內(nèi)存壓力。在具體實(shí)現(xiàn)方面,要注意對(duì)象的狀態(tài)處理(即只讀不修改,否則后續(xù)可能無法重復(fù)使用)
- 對(duì)象的數(shù)量太大從而導(dǎo)致對(duì)象內(nèi)存開銷加大——什么樣的數(shù)量才算大?這需要仔細(xì)的根據(jù)具體應(yīng)用情況進(jìn)行評(píng)估,而不能憑空臆斷。