軟件設計的哲學:第十一章 兩次設計

目錄編輯器

設計軟件是困難的,因此你對如何構建一個模塊或系統的最初想法不太可能產生最好的設計。若是您爲每一個主要的設計決策考慮多個選項,您將獲得一個更好的結果:設計兩次性能

假設您正在爲GUI文本編輯器設計管理文件文本的類。第一步是定義類將呈現給編輯器其他部分的接口;與其選擇第一個出如今腦海中的想法,不如考慮幾種可能性。一種選擇是面向行的接口,它具備插入、修改和刪除整行文本的操做。另外一個選項是基於單個字符插入和刪除的接口。第三種選擇是面向字符串的接口,它能夠跨行操做任意範圍的字符。你不須要肯定每種選擇的每一個特性;在這一點上,勾勒出幾個最重要的方法就足夠了。設計

嘗試選擇那些彼此大相徑庭的方法,這樣你會學到更多。 即便您肯定只有一種合理的方法,不管您認爲第二種設計有多糟糕,都要考慮採用第二種設計。思考該設計的弱點並將其與其餘設計的特色進行對比將是有益的。接口

在你草擬出可供選擇的設計方案後,列出每種方案的優缺點。對於接口最重要的考慮是對於高級軟件的易用性。在上面的例子中,面向行的接口和麪向字符的接口都須要在使用text類的軟件中進行額外的工做。在部分行和多行操做(如剪切和粘貼選擇)期間,面向行的界面將須要更高級別的軟件來分割和鏈接行。面向字符的接口將須要循環來實現修改多個字符的操做。這也值得考慮其餘因素:字符串

  • 一種替代方案的接口是否比另外一種簡單?在文本示例中,全部的文本接口都比較簡單。
  • 一個接口比另外一個接口更通用嗎?
  • 一個接口是否可以比另外一個接口更有效地實現?在文本示例中,面向字符的方法可能比其餘方法慢得多,由於它須要對每一個字符分別調用文本模塊。

一旦你比較了不一樣的設計,你就能更好地肯定最佳的設計。最好的選擇多是一個備選方案,或者您可能會發現能夠將多個備選方案的功能組合到一個比任何原始選擇更好的新設計中。it

有時,沒有一種選擇特別有吸引力,當這種狀況發生時,看看是否能夠提出其餘方案。使用您在最初的替代方案中肯定的問題來驅動新的設計。若是您正在設計文本類,而且只考慮面向行的和麪向字符的方法,那麼您可能會注意到每種替代方法都很笨拙,由於它須要更高級別的軟件來執行額外的文本操做。這是一個危險信號:若是有一個文本類,它應該處理全部的文本操做。爲了消除額外的文本操做,文本界面須要更緊密地匹配發生在高級軟件中的操做。這些操做並不老是對應於單個字符或單個行。這一行推理應該會爲文本提供面向範圍的API,從而消除了早期設計的問題。class

兩次設計原則能夠應用於系統的許多層次。對於模塊,您能夠首先使用這種方法來選擇接口,如上所述。而後您能夠在設計實現時再次應用它:對於text類,您能夠考慮諸如行鏈表、固定大小的字符塊或「間隙緩衝區」之類的實現。「實現的目標和接口的目標是不一樣的:對於實現來講,最重要的是簡單性和性能。在系統的更高層次上探索多種設計也頗有用,好比什麼時候爲用戶界面選擇特性,或者什麼時候將系統分解爲主要模塊。在每種狀況下,若是您能夠比較幾個備選方案,就更容易肯定最佳方法。軟件

設計兩次並不須要花費不少額外的時間。對於較小的模塊(如類),您可能不須要超過一兩個小時的時間來考慮替代方案。與您將花費幾天或幾周的時間來實現這個類相比,這只是一小部分時間。最初的設計實驗極可能會產生一個更好的設計,這將比花兩次時間來設計要好得多。對於較大的模塊,您將在最初的設計探索中花費更多的時間,可是實現也會花費更長的時間,並且更好的設計的好處也會更大。循環

我注意到「兩次設計」的原則有時很難被真正聰明的人所接受。當他們長大後,聰明的人發現他們對任何問題的第一個快速想法就足以得到一個好成績;沒有必要考慮第二種或第三種可能性。這很容易養成很差的工做習慣。然而,隨着這些人年齡的增加,他們會被提高到愈來愈困難的環境中。最終,每一個人都會到達一個臨界點,你的第一個想法再也不足夠好;若是你想得到真正好的結果,你必須考慮第二種可能,或者第三種,無論你有多聰明。大型軟件系統的設計就屬於這一類:沒有人有足夠的能力在第一次嘗試時就把它作好。文本編輯器

不幸的是,我常常看到聰明的人堅持執行他們腦海中出現的第一個想法,這致使他們沒有發揮出他們真正的潛力(這也讓他們在工做中感到沮喪)。也許他們潛意識裏認爲「聰明人第一次就能成功」,因此若是他們嘗試多種設計,那就意味着他們根本不聰明。事實並不是如此。這並非說你不聰明,問題是真的很難。此外,這是一件好事:解決一個須要仔細思考的難題要比解決一個根本不須要思考的簡單問題有趣得多。

兩次設計的方法不只提升了你的設計,也提升了你的設計能力。設計和比較多種方法的過程將教會您使設計更好或更差的因素。 隨着時間的推移,這將使你更容易排除糟糕的設計,並專一於真正偉大的設計。

相關文章
相關標籤/搜索