202102 演化式設計:測試驅動開發與持續重構 -- 心得

上完演化式設計:測試驅動開發與持續重構,課後兩個月補記心得和筆記。

專業有價

早在 2018 左右就聽說 91 的課,當時看到上課時間居然在半年後,而且一堂課要價超過一萬元,就一直處於觀望狀態而沒有報名課程。幸好在這期間我看了《刻意練習》後,就一直心心念念想找到利用「刻意練習」模式教學的課程,再加上我開始認同「專業有價」,花錢就能買到別人累積的功力,超級划算。於是,在剩下最後幾個名額時,趕緊手刀報名,心裡想不管發生什麼事,都不能妨礙我去上課,要是再不做出行動,現在這門課是開課前一年就額滿 ⋯⋯

從了解需求開始

  • 由實作的人去問出需求
  • 用具體的例子談需求,甚至用錯誤的例子誘導對方講出正確的需求

說到討論需求,近日有新的感想,我終於可以察覺出「問出需求」和「擬定做法」是兩回事。

以前很多時候,我只是在覆核 PM 提出的調整可不可行,而沒有去探究背後的需求,現在可以練習再多問『想做出調整的原因?』和問『什麼會想用這個方式調整?』,這樣才能有足夠的資訊選擇最適當的做法。另外,我發現我很習慣用簡短或沒整理過的描述和其他人討論事情,用具體的例子和其他人溝通是我還需要多練習的課題。

便利貼起手式

  • 拆解會需要的程式碼片段,可使用便利貼或 Mind Map 工具
  • 和團隊成員一起決定命名或 API 規格

以前我都會一邊設計程式一邊敲鍵盤,因為覺得與其花時間在腦袋一直空想,還不如直接就開始寫程式,邊理解需求邊寫程式還邊重構,自以為我真是會敏捷開發,但是常常發生 A 設計寫到一半覺得不夠好,應該要改成 B 設計,B 設計寫到一半發現有情境沒考慮到,所以一開始才會寫成 A 設計那樣,改過來又改回去,搞到最後沒時間好好梳理程式架構和流程。

所以二月週末上完課,週一進辦公室,我就乖乖到文具櫃去拿一本便利貼來用,仔細拆解會需要的程式碼片段,再開始敲程式碼,寫程式有明顯變得比較順,思路也比較周全,反而花比較少時間開發,對於 Task 的完成度更有信心。

安排測試案例,小步重構

  • 測試案例必須是使用情境,命名要描述 Domain,不能出現具體的例子名稱
  • 測試案例從最簡單的案例開始寫,如果要改太多就拆小一點

    最簡單的意思是:加最少的程式碼片段,或複製測試案例改最少的程式碼片段。

  • TDD 只需要列出可以把需要的程式碼片段開發完成即可,不用列出所有案例

我之前以為用排列組合列出所有測試案例,就是最系統化的方式,完全沒想過測試案例的順序是要刻意安排的,所以一次不會改動太多程式,比較沒有除錯壓力,搭配便利貼起手式一起服用更有效。先做好全局的思考,這時候再開始用 TDD 的方式寫程式:

  1. Baby Step:一次做少一點,然後該做的有做完(一個完整的使用情境)
  2. 紅燈 → 綠燈:無腦通過測試案例
  3. 綠燈 → 重構:從刻意產生重複的程式碼演進成 Production Code 設計

重構 Legacy Code

Legacy Code 是實務上最常會遇到的情況,通常 Legacy Code 沒有單元測試保護,所以就沒人敢改。
利用單元測試和強大的 IDE 工具自動產生程式碼做重構,安全地跳脫惡性循環:

  1. 整理代碼:刪除 comment、調整爛命名、多餘空白行、Temp Variables
  2. 整理流程:消除重複、凸顯意圖

    不要太早抽方法,會不容易看出重複,可用 Inline Method 回復 Method。

  3. 改邏輯要有對應的測試保護
  4. 分職責
    • 物件導向(高內聚):用物件模型模擬真實世界,把資料往物件堆,叫物件做事
    • Design Pattern(低耦合)

原則上設計心法就是用最簡單的方式滿足使用者情境,並且寫最少的防呆,參數越少越好用。

Keep it Simple, don’t overdesign your solution.

結論

[演化式設計:測試驅動開發與持續重構] 是 [針對遺留代碼加入單元測試的藝術] 和 [極速開發] 兩門課的集大成,上完課後仍需要不斷練習和反思,才能持續進步。原本課前預習就應該要先了解 Code SmellRefactoring 相關知識,但在上課前我沒有確實做到,現在要補下基本功,也藉此督促自己要熟練課堂上的重構練習。

相關文章