計算機革命是有關我們如何去思考的方式, 以及我們如何去表達自己的思考的一個革命。- SICP
應當避免控制中的復雜性,將精力集中到數據的組織上,以反映所模擬世界里的真實結構。- Joel Moses
Program to an 'interface', not an 'implementation'.
Favor 'object composition' over 'class inheritance'. - GoF
軟件的本質
一切工具都是為了解決人的問題,軟件也不例外。但人類世界的現實問題到軟件的解決方案的實現路徑跨越太大,無法一步躍遷,這就需要設計分解成一系列的躍遷步奏,這就是軟件設計的本質。
而編程的本質就是用編程語言對這一系列過程進行描述。所以編程語言是邏輯的載體和描述工具。
但就像一位大師說的“語言磨礪了我們的思維方式,也決定了我們的思考范圍”,所以不同的編程語言又反過來影響了軟件的定義。
從過程式范式來看,
軟件 = 數據 + 算法;
從面對對象范式來看,
軟件 = 對象 + 控制;
從函數式范式來看,
軟件 = 解釋 + 應用(eval-apply loop);
從邏輯范式來看,
軟件 = 邏輯 + 控制。
從數學模型來看,
軟件 = 計算模型 + 語義。
其中計算模型是對特定領域的數學抽象。語義是對特定領域的具象表達。
從計算機硬件模型來看,
軟件 = 數據 + 控制。
因為馮.諾依曼計算機模型的物理設計,數據和控制是分離的,運行在其之上的軟件,也必然受其影響。
而我們常說的軟件架構、設計模式、框架和庫,它們的一個顯著差異就是,
- 軟件架構是從問題域對軟件進行描述;
- 設計模式是從解決方案域對軟件進行描述;
- 框架是對一系列設計模式進行邏輯和概念上的封裝;
- 從調用關系上來說,框架:don't call us, we'll call you;庫: call me please。
雖然不同范式對軟件的理解和分解方式不盡相同,但都有異曲同工之處,即軟件分為兩部分:
- 一部分是數據,不管是叫對象、邏輯還是模型;
- 一部分是控制,不管是叫算法、解釋還是語義。
這就是軟件的本質:
軟件是數據和控制的有效結合,其中數據部分才是真正有意義的(What),控制部分只是影響數據部分的效率(How)。數據和業務或領域模型有關,無法標准化;但控制是可以標准化的,比如:遍歷數據、查找數據、多線程、並發、異步等,都是可以標准化的。
數據和控制的分離手段
如何有效表達數據和控制?如何抽象數據和控制,提高其表達能力?這篇文章有較詳細的介紹,本文就不再贅述。但在描述數據和控制之前,首先要分離數據和控制。具體到不同的編程范式,數據和控制分離的具體手段也有差異,如:
- 過程式編程:數據驅動,狀態機
- 面向對象:委托模式、策略模式、橋接模式、修飾模式、IoC/DIP、泛型
- 函數式編程:修飾器、管道、拼裝、lambda