在上一篇裡面,我們初步了解了OO設計,OO設計的最獨特之處在於他看待需求的方式。用這樣的方式 ,我們不需要急於確定軟件需要實現哪些流程、設計哪些功能點、制作哪些畫面,而是要關注需求中一 些更加基本的概念。首先根據這些概念開發出一些零件,然後把這些零件組裝起來實現需要的功能。用 這樣的方式,我們不需要一開始就去知道所有的業務需求,只需要知道一些比較重要的需求,就可以開 始開發了。這樣開發出來的程序不僅可以實現當前的需要,同時也是一個業務開發的平台,在這個平台 上可以不斷的開發新的功能。
這種設計思想有很多實際的例子,比如Microsoft Office。下面的 圖就展示了Excel裡面最基本的幾個對象:
Excel的各項功能都是建立在這個對象模型基礎上的。比如要實現設置字體 的功能,就可以這樣編寫:先打開一個字體對話框,使用者選擇字型、字號,然後把這個字體設置到區 域上:
Font font = CommonFontDialog.ChooseFont();
Application.ActiveWorkbook.ActiveSheet.Range("A1").Font = font;
Excel還把這些對象的引用暴露給了腳本引擎,於是我們就可以使 用VBA調用他們,實現我們自己想要的各種功能,這就是Office宏。我們可以編寫一段VB腳本,把鼠標選 中區域的單元格復制到另一個工作表中,然後把某一個的單元格的值賦值為一個公式,計算出我們需要 的數值。Excel不僅本身是一個好用的制表工具,他更是一個強大、易用的開發平台。使用者可以隨時根 據自己的想法,開發出需要的功能。一些大型的軟件系統都是具有這樣的特點,一開始就明確所有的功 能需求是不可能的,重要的是形成一個業務開發的平台,提供一些業務編程接口,在這個平台上就可以 不斷的開發出新的功能。這樣的開發方式不使用OO設計是很難實現的。
軟件的第一個維護者和第 一個使用者就是開發者本人,因此,開發迅速、功能靈活、維護簡單——這些特點在精心設 計的軟件中經常是同時具有的。
運用OO方法設計程序的時候會遇到的這樣困難:我們從需求中發 現了一些模糊的概念,但是怎樣才能根據這些概念建立合理的對象模型呢,到底哪些概念應該是一個類 ,哪些概念只應該是一個方法和屬性,這些類之間應該是什麼樣的關系?要解決這個問題,最根本的途 徑當然是盡量深入的了解需求(比如說翻翻會計原理,看看應收款未收和已收的時候應該如何記賬,其 中一個記賬原則也許就是一個重要的對象;協助用戶做一個供電方案,隨手畫出的草圖,或者某個計算 公式就是一個重要的對象)。在解決了一個個困難之後,有人總結了經驗,形成了一些解決特定問題的 固定套路,這樣的套路就是設計模式。
有些設計模式和OO沒有什麼必然的關系,比如層次模式, 消息模式。但是大部分設計模式都是在OO設計中形成的,這些模式可以幫助我們發現系統中的對象、設 計對象之間的關系。了解這些模式可以幫助我們把軟件設計的更加合理。並且,在探索需求的過程中, 我們也可以從模式中得到一些啟發,獲得設計的靈感,發現需求的真實面貌。
在上一篇我們看見 了“費用”這個類型:Fee,其實這就是一個簡單的設計模式:組合模式(Composite)。這 個類的結構如下:
Fee類型是他本身的一個聚合,可以使用 GetChildren方法得到某個費用包含的其他費用。如果一個費用沒有包含其他費用,他的金額就是由他自 己確定的,否則就是由他包含的費用相加確定的,這兩種情況對外界提供的都是相同的方法:GetValue 。這樣,我們想顯示一個賬單費用的時候,不用再去判斷他是否包含了其他的費用,調用起來就簡單了 很多。組合模式很好的體現了賬單費用的層次包含關系。
剛才的情況裡面,聚合類和元素類都是 同樣的類型。也有些情況他們分別屬於不同的類型。比如一個企業,他的營銷網絡是由下面一些元素組 成的:公司,市場部,直銷店,代理商,自由代理人,營業員。如同下面的情況:
公司按照行政區域建立了多個市場部,市場部建立了自己的直銷店,同時也 與很多代理商和獨立代理人進行合作,直銷店和代理商雇用了營業員。每天公司需要對每個銷售網點的 情況進行查詢和分析,需要知道他們定下了多少訂單、收了多少貨款、發展了多少新的客戶。
這 是一個比較復雜的結構關系,網點類型比較多,他們的銷售方式差異很大,各類數據統計的方式也不同 。並且在統計一些數值的時候,需要把下屬網點的數量加起來,再加上自身的數量。如果采用組合模式 ,就可以解決這種問題。