沒有事情像表面看起來那麼簡單 Nothing is as Simple as it Seems

作者:周思博 (Joel Spolsky)
譯:Paul May 梅普華
Monday, March 04, 2002
屬於 Joel on Software, https://www.joelonsoftware.com/2002/03/04/nothing-is-as-simple-as-it-seems/

CityDesk 有個小小的使用性問題。

問題是這樣的:你可以用選單由網路上匯入檔案(Import Web Page),也可以用滑鼠拖拉磁碟裡的檔案匯入 CityDesk。不過沒有選單可以匯入磁碟中的檔案,所以大家不是沒有發現可以這樣做,就是嘗試用 Import Web Page 功能匯入磁碟中的檔案,而後者當然也是不能用的。

我認為用兩頁的精靈可以輕易的解決這個問題。大概的方法是用精靈的第一頁問「你要由哪裡匯入資料?」,如果你選「磁碟」,第二頁就提示你輸入檔名;如果選擇「web」,第二頁就提示輸入 URL 路徑。

我幾乎要開始實作,不過還是停下來著手寫一份迷你規格。下面是這份規格的全文:

第一頁
你要由哪裡匯入資料?(磁碟 / Web)

第二頁(磁碟)
標準的開啟檔案對話盒 第二頁(Web)
有迷你網頁瀏覽器的URL輸入畫面

突然間我想到一件事。有辦法把通常由OS提供的開檔對話盒放在精靈裡嗎?

呃...

我去查過了。結果是可以的,不過不太好玩而且要花幾個小時工夫。那麼可以不用精靈來做嗎?我把規格重寫成:

兩個選單:
1) 由Internet匯入網頁 -> 顯示URL對話盒
2) 由磁碟匯入網頁 -> 顯示開檔對話盒

好多了。三分鐘的設計省了我幾小時的程式工夫。

如果你這輩子寫過 20 分鐘以上的程式,可能已經發現這個很好的基本原則:沒有事情像表面看起來那麼簡單.

就連複製一個檔案這麼簡單的動作都充滿陷阱。如果第一個參數是目錄會如何?如果第二個參數是檔案又如何?如果目的地已經有相同檔名的檔案又會怎樣?萬一沒有寫入權限又怎麼辦?

如果檔案拷到一半出錯要如何?如果目的地是需要認證才能繼續的遠端機器又如何?如果檔案很大而連線很慢,必須顯示進度欄時又會如何?萬一傳輸速度慢到幾乎完全不動...你要等多久才放棄並傳回錯誤訊息呢?

有個好方法可以用來面試應徵測試工作的人,就是要他針對一件簡單的操作,把所有可能出錯的地方全都列舉出來。微軟對面試測試人員有個經典題目:如何測試開檔對話盒?優秀的測試人員可以滔滔不絕地列出幾十種測試項目(在你選好檔案,要按「開啟」之前,另一個使用者把原本存在的檔案殺掉了)。

好了,所以我們得到一個定理:沒有事情像表面看起來那麼簡單。

軟體工程裡有另外一個定理,就是隨時隨地都要嘗試降低風險。其中一項必須避免的重大風險是進度風險,就是某件事花的時間比預期多。進度風險的壞處在於你會被老闆吼而很痛苦。如果你覺得這沒什麼,可以改由經濟觀點考慮進度風險的壞處。如果因為當初評估需要一週而決定要做某個功能,事後才發現其實需要20週,那麼前面的決策就錯了。如果你早知道需要20週很可能就會做不一樣的決定。而錯誤的決策愈多,印有你公司標誌的購物袋愈有可能流落到資產清算的倉庫,而同時間你的前執行長還在怨嘆「真慘啊,我們還沒有被 f***edcompany.com 報導前就倒了!」

「沒有事情像表面看起來那麼簡單」再加上「降低風險」只會導出一個結論:

你必須先做設計再去實作。

我很抱歉讓你失望了。沒錯,我知道你看過 Kent Beck 的書,而且現在認為不先設計而直接實作是正常的。很抱歉,這並正常。改程式就是沒法子和改設計文件「一樣簡單 」。大家一直都這樣說,不過這並不對。「現在我們都用 Java 和 XML 這種高階工具,幾分鐘就可以改好程式,為什麼不直接在寫程式時做設計呢?」我的朋友,你可以替你老媽裝上輪子,不過她並不會因而變成巴士。另外如果你自認能把錯用執行緒的檔案複製函數,重整改正成先佔多工的作法,而且速度和我寫這個句子一樣快,你根本就在自己騙自己(deep denial)。

無論如何,我不認為極限程式設計真的在提倡零設計。他們只是說「不要做無謂的設計」,而這一點是沒有問題的。不過大家聽到的不是這麼回事。大部份程式師都儘可能地找尋能不在實作前先做基本設計的藉口,所以他們就像捕蚊燈裡的蚊子一樣黏住「無設計」這個想法。這其實只是偷雞不著蝕把米的另類懶惰。我懶得先在紙上設計功能所以直接寫程式,程式做得不對只好再花時間修正,結果只會花更多的時間。還有更常見的狀況,就是程式寫錯了可是來不及改正,於是產品的品質低落,只好一直找藉口解釋東西為什麼「必須寫成這樣」。根本就是懶散又不專業。

當 Linus Torvalds 痛斥設計時談的是巨大的系統,這種系統必須逐漸演進,否則就會像 Multics 那樣死路一條。他說的並不是你的檔案複製程式。人們認為 Linus 有很清楚的計劃,確實知道往後要怎麼進行,無怪 Linus 會不怎麼看重設計。所以別上當了,這種作法很可能並不適合你。何況 Linus 比我們要聰明多了,他能做的事我們一般人是做不來的。

漸進式的設計和實作是好的。常常發行也是好的。不過就套裝軟體或大眾市場而言,頻繁的發行新版會讓客戶瘋掉,並不是個好主意,應該改成在內部密集的發行。太拘泥於設計細節會浪費時間,我從來沒看過哪個專案,會因不需動腦的流程圖或 UML 或 CRC 或是其他流行玩意而獲益。Linus 說的那些有一千萬行程式的超大型怪物系統應該要逐漸演進,因為人類確實不知道要如何設計那種規模的軟體。

不過當你坐下來要寫檔案複製的程式,或是計劃下一版軟體的功能時,一定要做設計。不要讓那些說法迷惑了你。

這些網頁的內容為表達個人意見。
All contents Copyright © 1999-2006 by Joel Spolsky. All Rights Reserved.