免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
最近访问板块 发新帖
查看: 784 | 回复: 0
打印 上一主题 下一主题

探索產生物件的技巧(終)間接產生物件的訴求:降低相依性 [复制链接]

论坛徽章:
0
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2007-10-20 13:14 |只看该作者 |倒序浏览

最常運用的生成模式,不脫Simple Factory Method、Singleton、Object Pool,以及Object Cache。若再妥善利用Reflection技巧,就更能降低物件之間的相依性。
這個系列的文章有一個中心思想,就是避免讓用戶端程式直接產生物件,而把產生物件的工作及責任交予另一個類別。
之所以這麼做有幾個主要的原因。首先,是要隔離用戶端程式碼對於被產生物件的認識。被譽為設計模式聖經本的四人幫大作《Design Patterns》一書中,開宗明義就強調「要針對介面,而不針對實作設計程式(Program To Interface,Not An Implementation)」。由用戶端自行產生物件,程式碼便接觸了它所要產生並使用的物件,也就直接認識了實作本身。
避免大海撈針的苦果
假使開發者放任用戶端程式碼直接碰觸物件的實作,日後當實作本身有了變化,便會影響到直接碰觸物件實作的所有用戶端。開發者在面臨此類變更時,最大的惡夢是要逐一找出散落於四處的用戶端程式碼,再逐一修改,有時候像是在「大海撈針」。
為了避免這類的情況,所以我們要避免讓用戶程式碼直接產生物件並使用,我們交由另一個類別負責產生實作類別,交由用戶端程式碼時,以介面的型態呈現,使得用戶端對物件的實作類別一無所知,也就將用戶端程式碼與改變的影響隔離。
集中控管並封裝邏輯
我們之所以要交由另一個類別為用戶端程式碼產生物件,還有一個重要的原因,就是要集中控管並且封裝產生物件的邏輯。有時候,開發者會隨著不同的情境產生實作不同但介面相同的物件,(例如認證實作類別LDAPAuthenticator與DBAuthenticator,都依循相同的介面Authenticator),交由用戶端自行判斷,很容易因為日後邏輯的變更,而造成「大海撈針」的下場。
所以我們將涉及這段邏輯的程式碼,全部集中在單一地點,並且加以封裝,使得外界無法碰觸。這麼一來,日後假使有所變更,也只要修改一處即可。
Simple Factory Method設計模式,雖然是泛Factory族系的設計模式中最簡單的,卻提供用戶端程式碼「Program To Interface」的機會,同時集中控管並封裝了產生實作類別的邏輯。以Simple Factory Method為基礎,可以輕易捕捉到其他泛Factory族系設計模式的重點。
Reflection的動態機制提供更多彈性
在認識Simple Factory Method之後,我們就能夠降低用戶端程式碼與它所欲使用的物件之間的關聯性,因為產生物件的責任交給了Simple Factory Method。Simple Factory Method封裝而且集中控管了產生物件的邏輯,但是對Simple Factory Method本身,仍然與實際要產生的實作物件有著一定程度的相依性。
為此,我們也介紹利用Reflection的技巧,能夠在Simple Factory Method程式中依據外部的組態設定,動態決定要產生的物件實作,而Simple Factory Method卻不需要寫入任何關於要產生的類別實作名稱。
在設計模式聖經本裡有摘要整理出一套規則,當需求有所變化,會導致重新設計的幾個共通原因,其中像:寫死類別名稱、寫死函式名稱、寫死在固定實作等,都是可以透過Reflection避免。
透過Reflection可以動態決定要產生的類別名稱、要呼叫的函式名稱,藉以提供更多的彈性,消弭更多的相依性。如果說Simple Factory Method切斷了用戶端程式碼與它所使用物件的相依性,那麼再加上如虎添翼的Reflection,更能進一步地斬斷Simple Factory Method自身與它所製造物件的關係。
Singleton控制系統中最多僅有單一實例
根據實際的開發經驗中,Simple Factory Method已能滿足許多產生物件的需求。而在本系列文中,繼續介紹了Singleton、Object Pool以及Object Cache等三種時常應用的模式。
Singleton是一個雖然簡單,卻幾乎是任何系統都會應用到的一個模式。Singleton是系統中單一且唯一的實例,通常做為系統中全面性工作的類別,而且具備資源集中控管的特性時,就適合套用。
例如,檢驗使用者身分是否正確的類別,系統只需要單一份實例就足以滿足所有的需要,系統並不需要多份實例提供不同的服務,所以就很適合採用Singleton的方式來設計。
Object Pool利用快取避免虛耗資源
Singleton控制系統中最多僅有單一實例,而Object Pool進一步擴充了Singleton的概念,同樣能控制系統中實例的個數,但允許系統中同時存在多份實例。應用程式可能會需要建立多個資料庫連線至資料庫進行查詢,也有可能需要建立多個執行緒同時並行地執行多個工作。
由於系統資源的限制,如果不限制建立的資料庫連線或執行緒的數量,那麼當資料庫連線或執行緒個數過多時,效能可能會因此而趨於低落。
除了系統資源限制的問題之外,某些特定的資源所產生或清理的代價過於高昂,倘若反覆的加以產生、清理,便有可能浪費過多的成本。而上述的這兩個問題,都可以透過套用Object Pool的設計解決。
運用Object Pool,用戶端的程式碼需要物件時,會從Object Pool中取得,而不再需要時,則將物件歸還至Object Pool。Object Pool會控管同時能被取得的物件個數,同時重複地使用用戶端程式碼所歸還的物件。透過Object Pool的機制,系統不會反覆地建立、摧毀物件,也能以Object Pool為中心,控管外部使用的物件數量,因而解決上述兩個問題。
Object Cache運用了電腦領域廣為人所熟悉的快取概念。套用Object Cache時,就和使用Object Pool一樣,用戶端程式碼從Object Cache取出所需的物件。當Object Cache中無法取得所需的物件時,再由用戶端程式碼或由Object Cache本身,重新產生一份新的物件,並置入Object Cache中。
倘若自Object Cache能取得所需的物件時,便毋需重新產生一份。這對於那種產生代價極為高昂的物件來說,可以避免耗費一再產生的成本。例如,對常見的網站系統來說,幾乎都會運用資料庫快取的技巧,提升運行的效能。
在應用資料庫快取時,系統會盡量自資料庫快取中取得資料庫查詢的結果,除非該資料所設定的期限過期,或者快取中不含所需的資料,否則便不需向資料庫重新查詢,可用的資料完全就在主記憶體中,存取的速度遠比向資料庫重新查詢來得快。
本文筆者試著總結本系列的一連串主題,而根本立意便是希望讓剛入門的新手程式人能夠明白,在用戶端程式碼中直接產生物件的缺點,並且介紹間接產生物件的方法,而這其中有許多方法都被歸類於設計模式中的生成模式(Creational Patterns)。
雖然有很多產生物件的方式,但最常運用的,不外是這一系列文章中所介紹到的Simple Factory Method、Singleton、Object Pool,以及Object Cache。在使用生成模式時,妥善利用Reflection的技巧,更可以大幅降低產生與被產生物件的類別之間的相依性。
《作者簡介》王建興
清華大學資訊工程系的博士研究生,研究興趣包括電腦網路、點對點網路、分散式網路管理、以及行動式代理人,專長則是Internet應用系統的開發。曾參與過的開發專案性質十分廣泛而且不同,從ERP、PC Game到P2P網路電話都在他的涉獵範圍之內。

本文来自ChinaUnix博客,如果查看原文请点:http://blog.chinaunix.net/u/32667/showart_404202.html
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP