如何從職責和協作中發現豐富物件?
從程式設計師角度來看:職責和協作是物件方法行為的兩種表現形式,物件內部行為稱為職責;物件之間互動行為稱為協作。但是職責和協作其實是物件內部行為或相互呼叫的來源,我們看到的程式碼往往是行為結果,為什麼物件中有這個方法行為,而不是那個物件行為,為什麼物件之間要有這種呼叫,為什麼不能放在一個物件中實現?
Martin Fowler曾經總結“重構”寫了一本書,書中羅列了很多重構方法,比如extract method,現在Eclipse工具重構refactor都有這些重構方法,但是在何種場景下使用這些重構方法?為什麼要將方法在物件之間遷移?如何能夠界定哪個方法行為和哪個物件更接近?如果我們從分析建模開始就引入職責和協作設計,一切都迎刃而解。
一個物件透過不同職責能夠扮演多個角色,從而實現不同業務場景情況下的業務功能,職責一旦複雜比較大,就會被切分,分配到兩個以上物件中,就形成了物件之間的協作。協作模型是描述“how” 和 “when” 和 “with whom.” 的動態行為,
軟體的互動協作使用如下Speak for Me軟體描述:
假設使用者是盲人或不能講話,躺在醫院病床上,她被囚禁了,不能用任何方式聯絡,除了眨眨她的眼睛,表“是”或“否”。她向Speak for Me發出字母訊息,軟體替代講話,用一個小的感測器監視她的眼睛眨,用來進行字母的選擇,並且能夠根據各自場景規則演算法猜測語句,供其選擇。她可以透過眨眼發出命令,比如眨眼發出”RE”讀取郵件,發出 “CH”尋求幫助。
該使用者是表達者,軟體是服務者,表達者驅動軟體為之服務,服務者隱藏了具體實現細節。如果我們隱藏了某個物件如何工作的實現細節,我們就可以在不影響使用者的情況下靈活地改變具體實現方式。
使用協作模型可以幫助我們分清WHAT和HOW,實現宣告式設計,達到DSM或DSL層面。
如果使用一群互相適合的物件在一起協作工作,支援一個大的職責,這是一個好的設計方式,DDD提出的聚合物件群也是這樣一個目的,兩者是一致的,下一步就是繼續關注物件是如何協作的,設計訊息(方法)執行步驟以及他們的引數和返回值。
通常有下面幾個職責和協作模式:
1.資訊擁有者模型,當一個物件是資訊擁有者,它的職責是知道這些資訊,不應該期望和其他物件協作獲得資訊。
有時資訊擁有者的職責將他們資料持久化(明確提出了物件自己實現自己儲存到資料庫是物件職責)。
資訊是否被快取,如果修改如何更新,這是如何協作的?(明確提出物件自己負責自己快取是物件職責)。
比如:線上銀行的介面,接受交易資料,然後傳給服務的提供者,這個服務將其儲存在“交易記錄”這個物件中。
這裡僅有的協作者就是“交易記錄”物件自己使用持久層技術服務把自己儲存到硬碟上。
2.組織結構模型。類似UML中常提到的聚合和組合,專門有一個結構組織者(父物件)來管理它的部件,比如Car和發動機 方向盤就是聚合關係,Car負責管理部件間的結構,這類似部門經理管理部門一樣,和Facade模式非常相似。
除此之外,結構組織者(父物件)還要關心結構本身是否需要持久化?誰負責做這些持久化?這些物件是否被一個結構掌握訪問?結構是否組織隱藏物件之間關係?或者將其暴露給協作?其他物件是否知道這種組織並訪問?
這些提問就可以幫助你實現父子物件之間方法行為的分配,實現封裝和開放的OO設計原則。總之,一般是父物件知道自己子物件,就要使用結構模型。
另外,還有其他模型,比如:服務提供者模型,這類似於DDD中的服務模型,還有控制者模型和協作者模型:控制者能區分事情,決定採取行動;協作者通常是讓它做什麼就做什麼,很少做決定,有一個領導和部下,方向戰略和戰術的關係。
協作者模型和前面的結構者模型是有區別的,協作者模型側重管理一群工作者的行為,而結構者管理一群物件,表達一種它們之間的高聚合檢視。類似GoF設計模型中行為模式和結構模式的區別。
比如:當使用者在編輯一個文件時,選擇儲存,軟體在儲存到檔案之前必須做幾種決策,即將儲存的格式 (HTML, text, PDF, etc.)、是否取一個檔名?監視使用者行為動作的物件將直接響應這些決策,或在協作者之間分享決策。
本人以前在批判面向資料庫設計軟體時,就以文件編輯為例子,你只要發出儲存命令,而不必關心是如何儲存的,者實際又是一個WHAT(什麼命令)和HOW(如何執行命令)的關注分離。
此外,還有介面模型,如何定義介面,介面分使用者介面 內部介面和外部介面,介面封裝了職責和協作,因此,提倡面向介面程式設計不是隻是使用介面語法就可以,也不只是使用面向介面的框架就可以,這些都是表面的,真正的是用介面表達物件的職責和協作。
物件設計:角色、責任和協作"(Object Design: Roles, Responsibilities, and Collaborations)一書還提出了分層的職責,如下圖;DDD提出了分層架構,但是層的職責功能以及之間如何互動是什麼沒有詳細定義。
總之,如果你非常熟悉GoF設計模型,特別是其中的行為模式,很多方面和職責協作是相通的,如果有命令、事件、呼叫、訪問、通訊、觀察、監視等行為發生,我們就認為有協作發生,反之亦然。
[該貼被banq於2010-02-09 17:25修改過]
相關文章
- 物件的責任與職責物件
- 從真實案例出發:如何在協作開發中避免誤解!
- 流程、規則和管理職責
- 女人的作業系統和程式設計師的職責薦作業系統程式設計師
- 使用 Linux cowsay 製作豐富多彩的節日問候Linux
- CQRS中的Command Bus和Event Bus職責區別
- iOS 開發 – 均衡程式碼職責iOS
- 學習搭建 Consul 服務發現與服務網格-有豐富的示例和圖片
- RK3588開發板豐富的功能介面
- Peritext:用於富文字協作的新型CRDT
- PHP實現職責鏈設計模式PHP設計模式
- 職責鏈模式模式
- MySQL DBA工作角色和職責介紹MySql
- vscode語音註釋, 讓資訊更豐富(中)VSCode
- 產品經理和產品負責人之間的職責是如何劃分? - Reddit
- 豐富的開發體驗和激動人心的使用者體驗:XAML
- MongoDB學習之豐富的索引MongoDB索引
- 急需經驗豐富的java高手Java
- NPDP|作為產品經理,如何愉快地與跨職能團隊協作?
- 如何實現Excel多人共享與協作Excel
- Laravel 專案實戰中如何快速整合 Emoji 表情包?Emoji 表情包太豐富了Laravel
- QA在整個專案中的職責和任務情況
- 初階技能:Android 應用異常如何豐富線索Android
- hadoop 實現HIVE和HBASE協作!HadoopHive
- 打破“過度簡化”:在豐富世界中重新解讀遊戲遊戲
- 增刪改是Respository的職責,還是Entity的職責?
- 免費提供運維專案,豐富簡歷和經歷運維
- Oracle DBA的職責Oracle
- 物件導向設計原則之單一職責原則物件
- 【cypress】4. 豐富的除錯工具除錯
- 10個豐富自我的機器學習專案機器學習
- 豐富的包(packages)生態系統Package
- 程式設計師豐富個人生活程式設計師
- 旅行保險公司工作豐富模型(轉載)模型
- 工作豐富化的步驟(轉載)
- 使用 LogProperties source generator 豐富日誌
- ZooKeeper系列(3)--基於ZooKeeper實現主從協作
- 如何利用 github 進行多人協作開發Github